PostgreSQL 分组集合新功能(GROUPING SETS,CUBE,ROLLUP)

2024-02-14 21:38

本文主要是介绍PostgreSQL 分组集合新功能(GROUPING SETS,CUBE,ROLLUP),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

PostgreSQL 分组集合新功能(GROUPING SETS,CUBE,ROLLUP)

实验环境

操作系统:windows 10 家庭中文版数据库系统: PostgreSQL 9.6.2

说明

postgresql从9.5版本开始新加入了group by的分组集合功能,提供了GROUPING SETS,CUBE,ROLLUP参数,使用方式与oracle完全一致,下面是实际测试说明

构建测试环境

创建表t并插入测试数据:

create table t(id int,name varchar(20),class int,score int);insert into t values(1,'math',1,90);
insert into t values(2,'math',2,80);
insert into t values(3,'math',1,70);
insert into t values(4,'chinese',2,60);
insert into t values(5,'chinese',1,50);
insert into t values(6,'chinese',2,60);
insert into t values(7,'physical',1,70);
insert into t values(8,'physical',2,80);
insert into t values(9,'physical',1,90);

结果:

test=# select * from t;id |   name   | class | score
----+----------+-------+-------1 | math     |     1 |    902 | math     |     2 |    803 | math     |     1 |    704 | chinese  |     2 |    605 | chinese  |     1 |    506 | chinese  |     2 |    607 | physical |     1 |    708 | physical |     2 |    809 | physical |     1 |    90
(9 行记录)

普通的group by

根据name和class字段求和:

test=# select name,class,sum(score)
test-# from t
test-# group by name,class
test-# order by name,class
test-# ;name   | class | sum
----------+-------+-----chinese  |     1 |  50chinese  |     2 | 120math     |     1 | 160math     |     2 |  80physical |     1 | 160physical |     2 |  80
(6 行记录)

grouping set

GROUPING SETS的每个子列表可以指定零个或多个列或表达式,并且与其直接在GROUP BY子句中的解释方式相同。 一个空的分组集合意味着所有的行都被聚合到一个组中(即使没有输入行存在,也是输出)。

test=# select name,class,sum(score)
test-# from t
test-# group by grouping sets((name),(class),())
test-# order by name,class
test-# ;name   | class | sum
----------+-------+-----chinese  |       | 170math     |       | 240physical |       | 240|     1 | 370|     2 | 280|       | 650
(6 行记录)

顺带一提,默认的group by语句相当于grouping set在grouping set后的参数填上所有group by的字段。如下:

test=# select name,class,sum(score)
test-# from t
test-# group by grouping sets((name,class))
test-# order by name,class
test-# ;name   | class | sum
----------+-------+-----chinese  |     1 |  50chinese  |     2 | 120math     |     1 | 160math     |     2 |  80physical |     1 | 160physical |     2 |  80
(6 行记录)

与不使用grouping set语句时的结果完全相同

rollup

* rollup((a),(b),(c))等价于grouping sets((a,b,c),(a,b),(a),()) *

test=# select name,class,sum(score)
test-# from t
test-# group by rollup((name),(class))
test-# order by name,class
test-# ;name   | class | sum
----------+-------+-----chinese  |     1 |  50chinese  |     2 | 120chinese  |       | 170math     |     1 | 160math     |     2 |  80math     |       | 240physical |     1 | 160physical |     2 |  80physical |       | 240|       | 650
(10 行记录)

等价于:

grouping sets((name,class),(name),())

cube

* cube((a),(b),(c))等价于grouping sets((a,b,c),(a,b),(a,c),(a),(b,c),(b),(c),()) *

test=# select name,class,sum(score)
test-# from t
test-# group by cube((name),(class))
test-# order by name,class
test-# ;name   | class | sum
----------+-------+-----chinese  |     1 |  50chinese  |     2 | 120chinese  |       | 170math     |     1 | 160math     |     2 |  80math     |       | 240physical |     1 | 160physical |     2 |  80physical |       | 240|     1 | 370|     2 | 280|       | 650
(12 行记录)

等价于:

grouping sets((name,class),(name),(class),())

实际应用

我遇到一个需求,需要在分组统计总和之外附加所有组的总和,命名为total:

test=# select coalesce(name,'total') as name,
test-# coalesce(class,0) as class,
test-# coalesce(sum(score),0) as sum_score,
test-# coalesce(round(avg(score),2),0) as avg_score
test-# from t
test-# group by grouping sets((name,class),())
test-# order by name,class
test-# ;name   | class | sum_score | avg_score
----------+-------+-----------+-----------chinese  |     1 |        50 |     50.00chinese  |     2 |       120 |     60.00math     |     1 |       160 |     80.00math     |     2 |        80 |     80.00physical |     1 |       160 |     80.00physical |     2 |        80 |     80.00total    |     0 |       650 |     72.22
(7 行记录)

这篇关于PostgreSQL 分组集合新功能(GROUPING SETS,CUBE,ROLLUP)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/709631

相关文章

PostgreSQL中rank()窗口函数实用指南与示例

《PostgreSQL中rank()窗口函数实用指南与示例》在数据分析和数据库管理中,经常需要对数据进行排名操作,PostgreSQL提供了强大的窗口函数rank(),可以方便地对结果集中的行进行排名... 目录一、rank()函数简介二、基础示例:部门内员工薪资排名示例数据排名查询三、高级应用示例1. 每

Java中的数组与集合基本用法详解

《Java中的数组与集合基本用法详解》本文介绍了Java数组和集合框架的基础知识,数组部分涵盖了一维、二维及多维数组的声明、初始化、访问与遍历方法,以及Arrays类的常用操作,对Java数组与集合相... 目录一、Java数组基础1.1 数组结构概述1.2 一维数组1.2.1 声明与初始化1.2.2 访问

Qt使用QSqlDatabase连接MySQL实现增删改查功能

《Qt使用QSqlDatabase连接MySQL实现增删改查功能》这篇文章主要为大家详细介绍了Qt如何使用QSqlDatabase连接MySQL实现增删改查功能,文中的示例代码讲解详细,感兴趣的小伙伴... 目录一、创建数据表二、连接mysql数据库三、封装成一个完整的轻量级 ORM 风格类3.1 表结构

PostgreSQL的扩展dict_int应用案例解析

《PostgreSQL的扩展dict_int应用案例解析》dict_int扩展为PostgreSQL提供了专业的整数文本处理能力,特别适合需要精确处理数字内容的搜索场景,本文给大家介绍PostgreS... 目录PostgreSQL的扩展dict_int一、扩展概述二、核心功能三、安装与启用四、字典配置方法

关于集合与数组转换实现方法

《关于集合与数组转换实现方法》:本文主要介绍关于集合与数组转换实现方法,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录1、Arrays.asList()1.1、方法作用1.2、内部实现1.3、修改元素的影响1.4、注意事项2、list.toArray()2.1、方

mysql表操作与查询功能详解

《mysql表操作与查询功能详解》本文系统讲解MySQL表操作与查询,涵盖创建、修改、复制表语法,基本查询结构及WHERE、GROUPBY等子句,本文结合实例代码给大家介绍的非常详细,感兴趣的朋友跟随... 目录01.表的操作1.1表操作概览1.2创建表1.3修改表1.4复制表02.基本查询操作2.1 SE

Golang如何用gorm实现分页的功能

《Golang如何用gorm实现分页的功能》:本文主要介绍Golang如何用gorm实现分页的功能方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录背景go库下载初始化数据【1】建表【2】插入数据【3】查看数据4、代码示例【1】gorm结构体定义【2】分页结构体

postgresql数据库基本操作及命令详解

《postgresql数据库基本操作及命令详解》本文介绍了PostgreSQL数据库的基础操作,包括连接、创建、查看数据库,表的增删改查、索引管理、备份恢复及退出命令,适用于数据库管理和开发实践,感兴... 目录1. 连接 PostgreSQL 数据库2. 创建数据库3. 查看当前数据库4. 查看所有数据库

Java Web实现类似Excel表格锁定功能实战教程

《JavaWeb实现类似Excel表格锁定功能实战教程》本文将详细介绍通过创建特定div元素并利用CSS布局和JavaScript事件监听来实现类似Excel的锁定行和列效果的方法,感兴趣的朋友跟随... 目录1. 模拟Excel表格锁定功能2. 创建3个div元素实现表格锁定2.1 div元素布局设计2.

HTML5实现的移动端购物车自动结算功能示例代码

《HTML5实现的移动端购物车自动结算功能示例代码》本文介绍HTML5实现移动端购物车自动结算,通过WebStorage、事件监听、DOM操作等技术,确保实时更新与数据同步,优化性能及无障碍性,提升用... 目录1. 移动端购物车自动结算概述2. 数据存储与状态保存机制2.1 浏览器端的数据存储方式2.1.