有的时候我们要从数据库里把数据组织成树结构再展现到页面上

像下面这样

今天我们用Group 和Grouping实现它,并总结一下它俩。

先看一下概念,再用代码一点一点去理解它们,最后我会给出完整的代码

Group By : 语句用于结合合计函数,根据一个或多个列对结果集进行分组。

Grouping :指示是否聚合 GROUP BY 列表中的指定列表达式。 在结果集中,如果 GROUPING 返回 1 则指示聚合;

返回 0 则指示不聚合。 如果指定了 GROUP BY,则 GROUPING 只能用在 SELECT <select> 列表、HAVING 和 ORDER BY 子句中。

ROLLUP :生成简单的 GROUP BY 聚合行以及小计行或超聚合行,还生成一个总计行。

让我们先建一个数据库,并添加一些数据

use master
go
if exists(select 1 from sysdatabases where name ='MyGroupDB')
ALTER DATABASE MyGroupDB SET SINGLE_USER with ROLLBACK IMMEDIATE
drop database MyGroupDB
go create database MyGroupDB
go
use MyGroupDB
go create Table Category
(
Category_ID int identity(1,1),
Category_Name varchar(100)
)
go
create Table Product
(
Product_ID int identity(1,1),
CategoryID int ,
Product_Name varchar(100)
)
go
insert into Category values('手机')
insert into Category values('台式机')
insert into Category values('数码相机')
go insert into Product values(1,'诺基亚')
insert into Product values(1,'三星')
insert into Product values(1,'苹果') insert into Product values(2,'HP')
insert into Product values(2,'IBM')
insert into Product values(2,'Dell') insert into Product values(3,'佳能')
insert into Product values(3,'尼康')
insert into Product values(3,'索尼')
go

看一下它们的数据

select *
from Category
left join Product on Category_ID = CategoryID

我们把它们用Group By分一下组

select Category_ID ,
Category_Name,
CategoryID,
Product_Name
from Category
left join Product on Category_ID = CategoryID
group by Category_ID ,CategoryID,Category_Name,Product_Name

我们看到这样和没有分组时展现的数据是一样的,让我们加上 ROLLUP 加上合计行

select Category_ID ,
Category_Name,
CategoryID,
Product_Name
from Category
left join Product on Category_ID = CategoryID
group by Category_ID ,CategoryID,Category_Name,Product_Name with rollup

我们看到了好多NULL数据,而且很有规律

这些规律我们可以用Grouping 看到

select Category_ID ,
GROUPING(Category_ID) as Category_IDGP,
Category_Name,
GROUPING(Category_Name) as Category_NameGP,
CategoryID,
GROUPING(CategoryID) as CategoryIDGP,
Product_Name,
GROUPING(Product_Name) as Product_NameGP
from Category
left join Product on Category_ID = CategoryID
group by Category_ID ,Category_Name,CategoryID,Product_Name with rollup

你会发现那些Null值就是Grouping 为1的时候

最后一行的合计是Categrory_ID的,我们不需要,CategoryID的合计我们也不需要我们要怎么去掉它们呢,在having 里

select Category_ID ,
GROUPING(Category_ID) as Category_IDGP,
CategoryID,
GROUPING(CategoryID) as CategoryIDGP,
Category_Name,
GROUPING(Category_Name) as Category_NameGP,
Product_Name,
GROUPING(Product_Name) as Product_NameGP
from Category
left join Product on Category_ID = CategoryID
group by Category_ID ,Category_Name,CategoryID,Product_Name with rollup
having GROUPING(Category_ID)=0 and GROUPING(CategoryID)=0

这样的结果 我们看到只有Product_Name的Grouping有为1 了

我们就是用它去实现这棵树

select
case GROUPING(Product_Name) when 1 then Category_Name else '' end as Category_Name,
case GROUPING(Product_Name) when 0 then Product_Name else '' end as Product_Name
from Category
left join Product on Category_ID = CategoryID
group by Category_ID ,Category_Name,CategoryID,Product_Name with rollup
having GROUPING(Category_ID)=0 and GROUPING(CategoryID)=0
order by Category_ID ,Product_Name

下面是完整的代码

use master
go
if exists(select 1 from sysdatabases where name ='MyGroupDB')
ALTER DATABASE MyGroupDB SET SINGLE_USER with ROLLBACK IMMEDIATE
drop database MyGroupDB
go create database MyGroupDB
go
use MyGroupDB
go create Table Category
(
Category_ID int identity(1,1),
Category_Name varchar(100)
)
go
create Table Product
(
Product_ID int identity(1,1),
CategoryID int ,
Product_Name varchar(100)
)
go
insert into Category values('手机')
insert into Category values('台式机')
insert into Category values('数码相机')
go insert into Product values(1,'诺基亚')
insert into Product values(1,'三星')
insert into Product values(1,'苹果') insert into Product values(2,'HP')
insert into Product values(2,'IBM')
insert into Product values(2,'Dell') insert into Product values(3,'佳能')
insert into Product values(3,'尼康')
insert into Product values(3,'索尼')
go select *
from Category
left join Product on Category_ID = CategoryID
-------------------------------------------------------- select Category_ID ,
Category_Name,
CategoryID,
Product_Name
from Category
left join Product on Category_ID = CategoryID
group by Category_ID ,CategoryID,Category_Name,Product_Name with rollup --------------------------------------------------------
select Category_ID ,
GROUPING(Category_ID) as Category_IDGP,
Category_Name,
GROUPING(Category_Name) as Category_NameGP,
CategoryID,
GROUPING(CategoryID) as CategoryIDGP,
Product_Name,
GROUPING(Product_Name) as Product_NameGP
from Category
left join Product on Category_ID = CategoryID
group by Category_ID ,Category_Name,CategoryID,Product_Name with rollup ----------------------
select Category_ID ,
GROUPING(Category_ID) as Category_IDGP,
CategoryID,
GROUPING(CategoryID) as CategoryIDGP,
Category_Name,
GROUPING(Category_Name) as Category_NameGP,
Product_Name,
GROUPING(Product_Name) as Product_NameGP
from Category
left join Product on Category_ID = CategoryID
group by Category_ID ,Category_Name,CategoryID,Product_Name with rollup
having GROUPING(Category_ID)=0 and GROUPING(CategoryID)=0 ------------------------- select
case GROUPING(Product_Name) when 1 then Category_Name else '' end as Category_Name,
case GROUPING(Product_Name) when 0 then Product_Name else '' end as Product_Name
from Category
left join Product on Category_ID = CategoryID
group by Category_ID ,Category_Name,CategoryID,Product_Name with rollup
having GROUPING(Category_ID)=0 and GROUPING(CategoryID)=0
order by Category_ID ,Product_Name

  

玩转数据库之 Group by Grouping的更多相关文章

  1. Group by Grouping

    玩转数据库之 Group by Grouping 有的时候我们要从数据库里把数据组织成树结构再展现到页面上 像下面这样 今天我们用Group 和Grouping实现它,并总结一下它俩. 先看一下概念, ...

  2. java中list集合的内容,如何使用像数据库中group by形式那样排序

    java中list集合的内容,如何使用像数据库中group by形式那样排序,比如:有一个 List<JavaBean> 他中包含了一些如下的内容JavaBean:name    mone ...

  3. Group By Grouping Sets

    Group by分组函数的自定义,与group by配合使用可更加灵活的对结果集进行分组,Grouping sets会对各个层级进行汇总,然后将各个层级的汇总值union all在一起,但却比单纯的g ...

  4. 数据库语法group by

    因为在做pgsql和mysql数据库时group by 有报错,但是在以前做mysql5.6的时候没有问题,虽然知道时违反了sql的语法问题,但是没有搞清楚什么原因,也找了不少资料,查找原因,在盆友的 ...

  5. 带你了解数据库中group by的用法

    前言 本章主要介绍数据库中group by的用法,也是我们在使用数据库时非常基础的一个知识点.并且也会涉及Join的使用,关于Join的用法,可以看我写的上一篇文章:带你了解数据库中JOIN的用法如有 ...

  6. Oracle PL/SQL之GROUP BY GROUPING SETS

    [转自] http://blog.csdn.net/t0nsha/article/details/6538838 使用GROUP BY GROUPING SETS相当于把需要GROUP的集合用UNIO ...

  7. GROUP BY GROUPING SETS 示例

    --建表 create table TEst1 ( ID ), co_CODE ), T_NAME ), Money INTEGER, P_code ) ); --插入基础数据 insert into ...

  8. group by <grouping sets(...) ><cube(...)>

    GROUP BY      GROUPING SETS() 后面将还会写学习 with cube,  with rollup,以及将它们转换为标准的GROUP BY的子句GROUP SET(), CU ...

  9. (4.6)sql2008中的group by grouping sets

    最近遇到一个情况,需要在内网系统中出一个统计报表.需要根据不同条件使用多个group by语句.需要将所有聚合的数据进行UNION操作来完成不同维度的统计查看. 直到发现在SQL SERVER 200 ...

随机推荐

  1. php多线程pthreads的安装与使用

    安装Pthreads 基本上需要重新编译PHP,加上 --enable-maintainer-zts 参数,但是用这个文档很少:bug会很多很有很多意想不到的问题,生成环境上只能呵呵了,所以这个东西玩 ...

  2. 【原创】大众点评监控平台cat的性能分析

    由于工作的原因,或者说我们之前内部监控设计和实现有点不满足现有的研发需求,所以调研了一下大众点评开源出来的cat这一套监控系统. 今天我们就来实验一把,cat的客户端埋点在我们的程序流程中上报数据到c ...

  3. JS高级程序设计2nd部分知识要点7

    例子: <!DOCTYPE html> <html lang="en"> <head>  <meta charset="UTF- ...

  4. REDIS 在电商中的实际应用场景(转)

    1. 各种计数,商品维度计数和用户维度计数 说起电商,肯定离不开商品,而附带商品有各种计数(喜欢数,评论数,鉴定数,浏览数,etc),Redis的命令都是原子性的,你可以轻松地利用INCR,DECR等 ...

  5. dba诊断之lock

    --产生锁的详细信息 select a.session_id, c.SERIAL#,d.spid, os_user_name, b.object_name,locked_mode,    c.sql_ ...

  6. sigemptyset,sigfillset,sigaddset,sigdelset,sigismember,sigprocmask,sigpendmask作用

    SYNOPSIS #include <signal.h> int sigemptyset(sigset_t *set); int sigfillset(sigset_t *set); in ...

  7. Hive UDF’S addMonths

    our project use hive 0.10 , and in the hiveql , we need use addMonths function builtin in hive-0.11. ...

  8. QEMU启动时插入tap虚拟网卡

    1.利用brctl命令创建虚拟网桥br0 brctl addbr br0 ifconfig br0 up //上述两条命令分开执行会导致网络断开 2.将虚拟网桥br0与物理网卡eth0绑定 brctl ...

  9. C++ 之 常量成员函数

    类的常量成员函数 (const member function), 可以读取类的数据成员,但是不能修改. 1  声明 1.1  const 关键字 在参数列表后,加 const 关键字,声明为常量成员 ...

  10. PHP中的include和require

    1.include语句 使用include语句可以告诉PHP提取特定的文件,并载入它的全部内容 <?php inlude "fileinfo.php"; //此处添加其他代码 ...