5

MySQL8.0-分组函数ROLLUP的基本用法(GROUPING) - 业余砖家

 1 year ago
source link: https://www.cnblogs.com/yeyuzhuanjia/p/17385827.html
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

一、ROLLUP简介

ROLLUP是GROUP BY子句的扩展。 ROLLUP选项允许包含表示小计的额外行,通常称为超级聚合行,以及总计行。 通过使用ROLLUP选项,可以使用单个查询生成多个分组集。

MySQL中的ROLLUP是用于 产生汇总输出的修饰符,包括表示超级汇总(较高级别)汇总操作的额外行。它使我们能够使用单个查询在多个分析级别上汇总输出。它主要用于为OLAP(在线分析处理)操作提供支持。

二、基本语法

以下是使用ROLLUP修饰符的语法:

SELECT 
    column1, column2, ...
FROM 
    table_name
GROUP BY
column1, column2,... WITH ROLLUP;

我们指定了 GROUP BY 子句,其中包括我们要基于其聚合数据的列名。最后,我们指定 WITH ROLLUP 修饰符以在另一行中获得超级聚合输出。

我们已经了解到GROUP BY查询已与诸如 MAX , MIN , SUM , COUNT , AVG 等将输出行按单列或多列进行分组。 ROLLUP修饰符是使用GROUP BY查询的选项,该查询包含用于表示小计的额外字段。这些额外的行称为超级汇总行,是总计行的总和。因此,ROLLUP修饰符使我们可以基于 GROUP BY子句中指定的列,在单个查询中创建一组集合行。

三、ROLLUP的使用

例如,假设我们有一个包含以下数据的表 " sales" :

CREATE TABLE IF NOT EXISTS sales
(
id      BIGINT   COMMENT  'ID',
years   INT  COMMENT '年份',
country VARCHAR(20)  COMMENT '国家',
product VARCHAR(32)  COMMENT  '产品',
sales  INT  COMMENT '销售额',
PRIMARY KEY(id)
);

insert into  sales VALUES
(1,2000,'Finland','Computer',1500),
(2,2000,'Finland','Phone',100),
(3,2000,'India','Calculator',150),
(4,2000,'India','Computer',1200),
(5,2000,'USA','Calculator',75),
(6,2000,'USA','Computer',1500),
(7,2001,'Finland','Phone',100),
(8,2001,'USA','Calculator',50),
(9,2001,'USA','Computer',2700),
(10,2001,'USA','TV',250);

如果要每年总结结果,我们将使用简单的GROUP BY子句,如下所示:

SELECT
years,
SUM(sales) AS total_sales  
FROM  sales  
GROUP BY years;

它将给出以下输出,显示每年的总销售额(总计):

2080940-20230509173714114-1812753082.png

在上面的查询中,分组集由列名称Year表示。如果我们需要在单个查询中一起生成多个分组集,则可以使用UNION ALL运算符,如下所示:

SELECT
years,
SUM(sales) AS total_sales
FROM  sales  
GROUP BY years
UNION ALL
SELECT
null as years,
SUM(sales) AS  total_sales
FROM  sales ;  

在此查询中,我们可以看到NULL列。这是因为 UNION ALL子句要求所有查询具有相同的列数。因此,为了满足此要求,我们在第二个查询的选择列表中添加了NULL。

在执行查询时,将获得以下输出:

2080940-20230509173808391-1263107249.png

年份列的输出中的NULL表示超级总计的总计值。由于此查询能够产生每年的总销售额以及总销售额的总和,因此,它有两个问题:

这使查询很长。由于数据库引擎在内部执行两个单独的查询并将结果集组合为一个输出,因此降低了查询的性能。

为解决这些问题,MySQL允许我们使用ROLLUP子句,该子句在一个查询中提供了两种分析级别。 ROLLUP子句是GROUP BY子句的扩展,该子句产生另一行并显示总计(超级聚合)值。

让我们在向WITH BY ROLLUP修饰符添加后看到结果子句显示所有年份的总计:

SELECT
years,
SUM(sales) AS total_sales
FROM sales
GROUP BY years WITH ROLLUP;

执行命令时,将得到如下输出:

2080940-20230509173856496-1290619260.png

在此输出中,我们可以在 Year列中看到 NULL 值,该值标识了超级汇总行。它清楚地表明ROLLUP子句不仅生成小计,而且给出了全年的总销售额。

如果GROUP BY子句有多个列,则ROLLUP修饰符具有更多的列。复杂的效果。在这种情况下, ROLLUP修饰符假定GROUP BY子句中指定的列之间的层次结构。每次列值发生变化时,查询都会在结果末尾生成一个额外的超级汇总摘要行。

例如,假设我们在GROUP BY子句中指定了三列为下方:

GROUP BY c1, c2, c3 WITH ROLLUP

ROLLUP修饰符采用以下层次结构:

c1 > c2 > c3

并生成以下分组集:

(c1, c2, c3)

(c1, c2)

请参阅以下查询以更清楚地说明它:

SELECT
years,
country,
product,
SUM(sales) AS total_sales
FROM sales
GROUP BY years, country, product ;

如果没有ROLLUP,则基于GROUP BY子句中指定的多个列的销售表摘要如下所示。在这里,我们将仅在年份/国家/产品分析级别获得摘要值。

2080940-20230509174011229-483533705.png

添加ROLLUP后,查询会产生一些额外的行:

SELECT
years,
country,
product,
SUM(sales) AS total_sales
FROM sales
GROUP BY years, country, product WITH ROLLUP;

请参见以下输出:

2080940-20230509174026784-1200707964.png

以上输出在以下四个级别生成信息: 分析,说明如下:

首先,给定年份和国家/地区的每组产品行都会生成一个额外的超级汇总摘要行,该行显示所有产品的总数。它将产品列设置为NULL。接下来,给定年份的每组行都会生成一个额外的超级汇总摘要行,该行显示所有国家和产品的总计。它将"国家和地区"和"产品"列设置为NULL。最后,对于所有其他行,它会生成一个额外的超级汇总摘要行,该行显示所有列的总计。它将Years,Country和Products列设置为NULL。

四、GROUPING()函数

GROUPING()函数用于检查结果集中的NULL是否表示常规分组值,超汇总值或总计。当超级汇总行中出现NULL时,它返回1、否则,它将返回0。

我们可以在选择列表, HAVING 子句和 ORDER BY 子句中使用GROUPING()函数。

请参阅以下查询:

SELECT
years,
country,
product,
SUM(sales) AS total_sales,
GROUPING(years),
GROUPING(country),
GROUPING(product)
FROM sales
GROUP BY years, country, product WITH ROLLUP;

当超级集合行中 Years 列中的NULL出现时, GROUPING(Years)返回1,我们将得到以下输出。否则,它将返回零。

类似地,当"超级汇总"行中"国家/地区"列中的NULL为空时, GROUPING(Country)将返回1、否则,它将返回零。

此外,当超级汇总行中"产品"列中的NULL出现时, GROUPING(produce)返回1、否则,它将返回零。

2080940-20230509174119774-257795851.png

我们还可以使用GROUPING()函数来替代超级汇总NULL值的有意义的标签,而不是直接显示。

以下查询说明了如何将 IF()函数与GROUPING()函数组合以替换标签"年份","国家/地区"和"产品"列中的超级汇总NULL值:

SELECT
 IF(GROUPING(years), 'All years', years) AS years,
 IF(GROUPING(country), 'All countries', country) AS country,
 IF(GROUPING(product), 'All products', product) AS product,
 SUM(sales) AS Total_Sales
FROM sales
GROUP BY years, country, product WITH ROLLUP;

我们将得到如下输出:

2080940-20230509174157253-827293660.png

如果我们在其中有多个参数GROUPING()函数,它将返回代表位掩码的输出,该掩码合并了每个表达式的结果。在这里,最低位产生最右边参数的结果。下面的示例将按以下方式进行评估:

示例: 分组(年份,国家/地区,产品)

  result for GROUPING(product)

+ result for GROUPING(country) << 1

+ result for GROUPING(years) << 2

使用多个参数GROUPING()函数示例:

SELECT
years,
country,
product,
SUM(sales) AS Total_Sales,
GROUPING(years,country,product) AS Grouping_Result
FROM sales
GROUP BY years, country, product WITH ROLLUP;

它将给出以下输出:

2080940-20230509174229856-1452473731.png

如果任何参数具有超级聚合的NULL值,则此GROUPING()的结果将为非零。在这种情况下,它将仅返回超级聚集的行,并使用以下查询过滤常规的分组行:

SELECT
years,
country,
product,
SUM(sales) AS Total_Sales
FROM sales
GROUP BY years, country, product WITH ROLLUP
HAVING GROUPING(years, country, product) <> 0;

它将给出以下输出:

2080940-20230509174309328-356779110.png

Recommend

  • 105
    • blog.soliloquize.org 7 years ago
    • Cache

    Boost.Python C++导出基本用法

    Boost.Python C++导出基本用法 發表於 2017-12-22 07:30:34   用一些简单的例子来记录下...

  • 95

    sed基本用法(图片)

  • 68

    setfacl命令可以用来细分linux下的文件权限。chmod命令可以把文件权限分为u,g,o三个组,而setfacl可以对每一个文件或目录设置更精确的文件权限。换句话说,setfacl可以更精确的控制权限的分配。比如:让某一个用户对某一个文件具有某种权限。这种独立于传统的u,g,o...

  • 51
    • 掘金 juejin.im 6 years ago
    • Cache

    MongoDB的基本用法

    1 前言 MongoDB是一个基于分布式文件存储的开源数据库系统。 MongoDB 将数据存储为一个文档,数据结构由键值(key=&gt;value)对组成。MongoDB 文档类似于 JSON 对象。字段值可以包含其他文档,数组及文档数组。 2 安装(mac

  • 42
    • blog.poetries.top 6 years ago
    • Cache

    Koa2基本用法

    Koa 就是一种简单好用的 Web 框架。它的特点是优雅、简洁、表达力强、自由度高 1.1 架设 HTTP 服务 只要三行代码,就可以用 Koa 架设一个 HTTP 服务。 co...

  • 25

    版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/kesalin/article/details/86713720 并行计算库充分利用多核的优势,通过并行运算提高程序效率,业界有两个知名的 c++

  • 57

    上次说了镜像和容器的基本操作和两者的关系,这次咱们一起说说定制镜像脚本Dockfile。 (一)Dockerfile Dockerfile 是一...

  • 6

    V2EX  ›  Python pandas 如何将分组的 value 传入 apply 函数中   ErenJaeger · 3 小时 22 分...

  • 9

    CUBE, ROLLUP, COMPUTE, COMPUTE BY, GROUPING SETS The CUBE and ROLLUP operators are useful in generating reports that contain subtotals and totals. There are extensions of the GROUP BY clause...

  • 7

    解析数仓OLAP函数:ROLLUP、CUBE、GROUPING SETS 摘要:Ga...

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK