You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在不使用子查询或冗余连接的情况下查询分组、分组总计及总计?

解决方案:用ROLLUP/GROUPING SETS实现分组、分组总计与全局总计

嘿,看来你已经在琢磨分组统计的最佳姿势了!其实不用子查询或者多余连接的话,用SQL标准里的ROLLUP或者GROUPING SETS就能完美解决你的需求——这俩就是专门用来生成分组、分组总计和全局总计的工具,完全符合你的要求。

先来说说ROLLUP:分层统计的首选

如果你需要的是分层递进的统计结果(比如先按「区域+产品」分组统计,再出每个区域的总计,最后出全局总计),ROLLUP是最顺手的。它会根据你指定的分组字段层级,自动生成各级总计行,全程不用额外子查询或连接。

举个实际例子,假设我们有个sales销售表,结构是这样的:

CREATE TABLE sales (
    region VARCHAR(50),  -- 销售区域
    product VARCHAR(50), -- 产品名称
    amount DECIMAL(10,2) -- 销售额
);

要同时拿到「区域+产品的分组统计」、「区域总计」和「全局总计」,直接这么写就行:

SELECT
    region,
    product,
    SUM(amount) AS total_sales
FROM sales
GROUP BY ROLLUP(region, product);

返回的结果会分成三类行:

  • 当region和product都有具体值时,这是单个产品的分组销售额
  • 当product为NULL、region有值时,这是对应区域的总计
  • 当region和product都为NULL时,这是所有数据的全局总计

如果想让总计行的显示更友好(比如把NULL换成「全部区域」「全部产品」),可以用GROUPING()函数判断是否是总计行:

SELECT
    CASE WHEN GROUPING(region) = 1 THEN '全部区域' ELSE region END AS region,
    CASE WHEN GROUPING(product) = 1 THEN '全部产品' ELSE product END AS product,
    SUM(amount) AS total_sales
FROM sales
GROUP BY ROLLUP(region, product);

灵活自定义统计组合?用GROUPING SETS

如果你不需要严格的分层,而是想灵活指定要统计的分组组合(比如只需要「区域+产品的分组统计」和「全局总计」,跳过区域总计),那GROUPING SETS更适合。它允许你直接列出所有想要的统计维度组合:

SELECT
    region,
    product,
    SUM(amount) AS total_sales
FROM sales
GROUP BY GROUPING SETS(
    (region, product),  -- 按区域+产品分组统计
    ()                  -- 全局总计
);

要是需要区域总计+全局总计,也可以直接加进去:

GROUP BY GROUPING SETS(
    (region, product),
    (region),
    ()
);

为啥这俩方法符合你的要求?

  • 完全不需要子查询:所有统计逻辑都在一个SELECT语句里完成,不用嵌套查询
  • 不需要额外连接:直接基于原表的GROUP BY扩展功能实现,没有多余的表关联操作

你之前尝试用PARTITION BY的思路其实是窗口函数的方向,但窗口函数是给每行原数据附加统计值,而这里我们需要的是聚合后的分组行+总计行,所以ROLLUP/GROUPING SETS才是更直接的解决方案,也不会和GROUP BY产生冲突。

内容的提问来源于stack exchange,提问作者user45867

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 08:34:08