17、SQL Server 汇总数据之计算总计数据

系统 1711 0

SQL Server 汇总数据之计算总计数据

虽然Reportin Service能够轻松地计算总计和小计,而无须查询做额外的工作。但实

践表明,向应用程序提供总计,让其在窗体或网页底端显示它可能很有用。

接下来的三个聚合命令将可以提供很好的解决方案。

一、Rollup 与Cube

两者基本语法一致:

group by ....

with  rollup | cube

聚合函数Rollup 和Cube在一个独立的行中计算出小计和总计,并在分组依据列中包

含空值,以指出对应的值为总计。Rollup生成分组依据列的小计和总计行,而Cube扩展

了这种功能,为每个分组依据列生成总计和小计行,有一个名为grouping()的函数,它在行为总计或小计时返回真(1),否则返回0。

如:

--查出工资,并根据部门进行分组,得出总计小计

select 

case grouping(C.bmname)

when 0 then C.bmname

when 1 then  '工资总计'

end as 部门名称

,sum(A.basic_gz+A.jiaban_gz+A.jiangjin) 部门工资 from gongzi A 

inner join yuangong B on A.ygid=B.id

inner join bumen C on B.bmID=c.id

group by C.bmname

with Rollup

--如果group by有多列,则还会返回小计,不只是总计

结果:

部门名称 部门工资

管理部      702

技术部      5469

客户部      1878

销售部      2200

工资总计  10249

 

 

分组依据多列:

--查出工资,并根据部门进行分组,得出总计小计

select 

case grouping(C.bmname)

when 0 then C.bmname

when 1 then  '工资总计'

end as 部门名称

,sum(A.basic_gz+A.jiaban_gz+A.jiangjin) 部门工资 from gongzi A 

inner join yuangong B on A.ygid=B.id

inner join bumen C on B.bmID=c.id

group by C.ID,C.bmname

with Rollup

--如果group by有多列,则还会返回小计,不只是总计

结果:

部门名称 部门工资

技术部     5469

工资总计 5469

管理部      702

工资总计  702

销售部      2200

工资总计 2200

客户部     1878

工资总计 1878

工资总计 10249

注:rollup放在group by 子句的后面,命令SQL Server生成一个总计行

如果使用的是cube,那么总计行与小计行的显示全部放在最后,且支持像rollup分组小计

,直接跟着分组后。这是对rollup的一个扩展。

二、compute 与compute by 

 

Compute子句,不是创建聚合查询,而是在常规查询后面添加一个聚合查询。该查询

返回一个包含明细数据行的常规结果集,然后加上几行,其中包含该结果集的汇总信息。

compute  聚合函数(列名1),聚合函数(列名2) [by]  分组依据列

注:加上了by就有了分组小计,而不只是总计,且不可与group by 共同使用,这是为了

向后兼容才提供的,一般使用Rollup 与cube

三、创建交叉表查询

虽然聚合查询能够根据多个列进行分组,但结果分行排列的,不太方便快速查看数据

。交叉表查询将分组依据列(或一维)逆时针旋转90°,将其变成结果集中的列。

如:

Category South East West Total

X 100  0  20  100

Y 200  300  50  550

Z 0 0   100     100

这是一个根据种类来进行分组,其中每个小组计算的是这种类别各个地区对应的销售量,

以及这种类别总销售量。

局限性:分行排列的Group by查询可以有多个聚合函数,而交叉查询只能显示一种

度量方式(只能计算一种聚合函数)。

注:术语:交叉表查询,描述的是结果集的外观,而不是创建交叉表的方法。

有多种方法生成交叉表。

四、固定列交叉表查询

创建包含已知的固定列交叉表查询的方法有三种。

1、使用相关子查询。2、使用Case表达式

3、使用透视

1、使用相关子查询

性能差,对于每个分组依据列的每个度量方式实例执行一次子查询。

如:

Select R.Category,

(select Sum(Amount) from RawData where Region='South' and 

Category=R.category ) as 'South',

(select Sum(Amount) from RawData where Region='North' and 

Category=R.category ) as 'North',

(select Sum(Amount) from RawData where Region='East' and 

Category=R.category ) as 'East',

(select Sum(Amount) from RawData where Region='West' and 

Category=R.category ) as 'West',

Sum(Amount) as Total

from RawData R

group by Category

2、使用Case表达式

使用Case表达式来筛选将被汇总的数据,而不是在相关子查询中筛选数据,这样

查询引擎可以将整个交叉表查询作为单个基于数据集的操作进行处理。

注:最适用方便的创建交叉表查询的方法

如:

Select R.Category,

sum(Case Region when 'South' then Amount else 0 end) as South,

sum(Case Region when 'North' then Amount else 0 end) as North,

sum(Case Region when 'East' then Amount else 0 end) as East,

sum(Case Region when 'West' then Amount else 0 end) as West,

Sum(Amount) as Total

from RawData R

group by Category

order by Category

这个查询没有使用任何Where子句来筛选RawData表中的数据,Group by 子句根据类

别对数据集进行划分。然后执行聚合函数为每个类别创建一个结果行。

注:该查询使用了一个技巧,在Sum()中使用了一个Case表达式,这样每列只考虑

一个地区的值。

3、使用透视

这种方法它在From子句执行聚合函数。并创建一个交叉表,将其作为数据源,

如将Pivot看作一个用作数据源的表值函数,则它接受两个参数。

第一个参数是用于对交叉表的值进行计算的聚合函数,第一个参数列出了被透视

的列。

基本语法:

(数据源)

PIVOT

(聚合函数)

条件

五、动态交叉表查询

使用PIVOT和游标实现。

 


 

17、SQL Server 汇总数据之计算总计数据


更多文章、技术交流、商务合作、联系博主

微信扫码或搜索:z360901061

微信扫一扫加我为好友

QQ号联系: 360901061

您的支持是博主写作最大的动力,如果您喜欢我的文章,感觉我的文章对您有帮助,请用微信扫描下面二维码支持博主2元、5元、10元、20元等您想捐的金额吧,狠狠点击下面给点支持吧,站长非常感激您!手机微信长按不能支付解决办法:请将微信支付二维码保存到相册,切换到微信,然后点击微信右上角扫一扫功能,选择支付二维码完成支付。

【本文对您有帮助就好】

您的支持是博主写作最大的动力,如果您喜欢我的文章,感觉我的文章对您有帮助,请用微信扫描上面二维码支持博主2元、5元、10元、自定义金额等您想捐的金额吧,站长会非常 感谢您的哦!!!

发表我的评论
最新评论 总共0条评论