Skip to content

第二章|聚合、分组与汇总 ​

本章目标 ​

学习如何使用聚合函数对数据进行统计和汇总,掌握 GROUP BY 分组、HAVING 过滤,理解聚合与普通查询的区别。

从简单的 COUNT 和 SUM 开始,理解聚合函数的工作原理,学会用 GROUP BY 按列分组,用 HAVING 过滤分组结果,最后掌握多列分组和 ROLLUP 小计。

学习路径 ​

按顺序阅读以下文章,每篇包含讲解、示例和练习:

  1. 聚合函数:COUNT、SUM、AVG、MIN、MAX
    使用聚合函数统计数据,理解聚合函数与普通列的区别。

  2. GROUP BY:按列分组
    按一列或多列分组,对每组进行聚合计算。

  3. HAVING:分组后过滤
    使用 HAVING 过滤分组结果,理解 WHERE 和 HAVING 的区别。

  4. 多列分组与 ROLLUP
    按多列分组,使用 ROLLUP 生成小计和总计。

关键概念 ​

聚合函数将多行合并为一行 ​

聚合函数对一组行进行计算,返回单个值:

sql
-- 普通 SELECT:返回多行
SELECT age FROM users;
-- 结果:30, 25, 35, 28, NULL(5 行)

-- 聚合 SELECT:返回一行
SELECT COUNT(*) FROM users;
-- 结果:5(1 行)

GROUP BY 创建分组 ​

GROUP BY 将数据分成多个组,对每组分别聚合:

sql
-- 每个年龄段有多少人
SELECT age, COUNT(*) 
FROM users 
GROUP BY age;

结果:每个不同的年龄对应一行聚合结果。

WHERE vs HAVING ​

  • WHERE:在分组前过滤行(基于原始数据)
  • HAVING:在分组后过滤组(基于聚合结果)
sql
-- WHERE:年龄大于 25 的用户有多少人
SELECT COUNT(*) FROM users WHERE age > 25;

-- HAVING:哪些年龄段有超过 1 个人
SELECT age, COUNT(*) 
FROM users 
GROUP BY age 
HAVING COUNT(*) > 1;

执行顺序 ​

sql
SELECT column, aggregate_function(column)  -- 5. 选择列和聚合结果
FROM table                                  -- 1. 从表中获取数据
WHERE condition                             -- 2. 过滤行
GROUP BY column                             -- 3. 分组
HAVING aggregate_condition                  -- 4. 过滤分组
ORDER BY column                             -- 6. 排序
LIMIT n;                                    -- 7. 限制行数

前置知识 ​

  • 掌握 SELECT、WHERE、ORDER BY(第一章)
  • 理解 NULL 的处理
  • 能够创建表和插入数据

后续章节 ​

完成本章后,继续学习:

练习答案 ​

本章所有练习的答案和详细解释:第二章练习答案

深入阅读 ​

为什么 SELECT 中不能混用聚合和非聚合列? ​

sql
-- 错误
SELECT name, COUNT(*) FROM users;

这个查询有歧义:name 是多行,COUNT(*) 是一行,数据库不知道应该返回几行。正确做法是要么只用聚合函数,要么用 GROUP BY。

NULL 在聚合中如何处理? ​

大多数聚合函数会忽略 NULL:

  • COUNT(*) 计数所有行(包括 NULL)
  • COUNT(column) 只计数非 NULL 行
  • SUM/AVG/MIN/MAX 忽略 NULL

返回SQL 学习路线 · 开始第一节

用心记录每一步成长