Oracle 聚合实现小计、合计 (GROUP BY ROLLUP)

1.先创建一个测试表

-- Create table 水果月销售记录表
create table C_FRUITS_SALES_RECORD_T
(
  quarter VARCHAR2(20),--季度
  month   VARCHAR2(20),--月份
  apple   NUMBER,--苹果销量
  banana  NUMBER,--香蕉销量
  orange  NUMBER--橘子销量
)

导入测试数据

   QUARTERMONTHAPPLEBANANAORANGE
1第一季度1509080
2第一季度2659460
3第一季度38011055
4第二季度412011550
5第二季度57512045
6第二季度66512550
7第三季度78011550
8第三季度88013060
9第三季度99511080
10第四季度1012090120
11第四季度1113585160
12第四季度128080120

现在我们对销售数据出一张统计报表,要求对每季度数据进行小计,所有数据进行合计应该怎么做呢?

我们可能想到使用要用union对明细数据和统计数据进行合并输出,或者在前端进行遍历后生成统计数据

2.使用ROLLUP字句

现在我们有更好的选择,使用RollUp

RollUp是Group By函数的字句,用于对分组数据产生统计数据

针对上述需求我们可以用一下SQL实现

SELECT NVL(T.QUARTER, '合计') AS QUARTER,
       NVL(T.MONTH, '小计') AS MONTH,
       SUM(T.APPLE) AS APPLE,
       SUM(T.BANANA) AS BANANA,
       SUM(T.ORANGE) AS ORANGE
  FROM C_FRUITS_SALES_RECORD_T T
 GROUP BY ROLLUP(T.QUARTER, T.MONTH)
 ORDER BY T.QUARTER, T.MONTH

查询结果如下:

   QUARTERMONTHAPPLEBANANAORANGE
1第一季度1509080
2第一季度2659460
3第一季度38011055
4第一季度小计195294195
5第三季度78011550
6第三季度88013060
7第三季度99511080
8第三季度小计255355190
9第二季度412011550
10第二季度57512045
11第二季度66512550
12第二季度小计260360145
13第四季度1012090120
14第四季度1113585160
15第四季度128080120
16第四季度小计335255400
17合计小计10451264930

那假如我们只需要合计,不要小计呢?也很简单,使用下边的代码

SELECT NVL(T.QUARTER, '合计') AS QUARTER,
       NVL(T.MONTH, '小计') AS MONTH,
       SUM(T.APPLE) AS APPLE,
       SUM(T.BANANA) AS BANANA,
       SUM(T.ORANGE) AS ORANGE
  FROM C_FRUITS_SALES_RECORD_T T
 GROUP BY ROLLUP((T.QUARTER, T.MONTH))
 ORDER BY T.QUARTER, T.MONTH

大家有注意到区别在哪了吗?

第一个是:GROUP BY ROLLUP(T.QUARTER, T.MONTH)

第二个是:GROUP BY ROLLUP((T.QUARTER, T.MONTH))

我们可以理解为 ROLLUP 括号 中的每个栏位都是一个维度,ROLLUP会按照顺序为 维度生成统计数据,添加在结果集中,而二级括号可以把几个栏位看做一个整体当做一个维度。

如:ROLLUP(A,B,C,D)会在结果集中添加(A,B,C,D)、 (A,B,C)、(A,B)、(A)、(null) 五种 统计数据

    而ROLLUP((A,B),C,D)会在结果集中添加 (A,B,C,D)、(A,B,C)、(A,B)、(null) 四种 统计数据

你也可以使用  GROUP BY  C, D ,ROLLUP((A, B)) 等方法去实现具体需求。

如果觉得有些乱,可以用一下代码,调整  GROUP BY 和 ROLLUP中的栏位看看输出结果

SELECT A, B, C, D, SUM(N)
  FROM (SELECT 1 AS A, 2 AS B, 3 AS C, 4 AS D, 5 AS N FROM DUAL)
 GROUP BY ROLLUP(A, B, C, D)

3.辅助函数

(1)GROUPING()函数:传入一列,用于判断是否为统计行,如上边示例的NVL(T.QUARTER, '合计') AS QUARTER,NVL(T.MONTH, '小计') AS MONTH 可以写作DECODE(GROUPING(T.QUARTER), 1, '合计', T.QUARTER) AS QUARTER,DECODE(GROUPING(T.MONTH), 1, '小计', T.MONTH) AS MONTH

(2)GROUP_ID()函数:无参数,相同分组出现的次数,可以用于过滤重复数据

(3)GROUPING_ID()函数:多列参数,对多列依次使用GROUPING()并对多列结果进行拼接成二进制数值,再转十进制输出结果,如上边 GROUPING_ID(T.QUARTER, T.MONTH) 小计行返回1,合计行返回3

4.相关函数

(1)PIVOT:行转列函数,假如你表格中每种水果不是单独存储,是用一列 种类 的栏位来标示时,你可能需要用到PIVOT函数,具体使用方法可以搜索一下,后边有时间我会详细写一下

  • 6
    点赞
  • 42
    收藏
    觉得还不错? 一键收藏
  • 4
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值