Group By、Having用法总结(常见踩雷点总结—SQL)

Group By、Having用法总结

在这里插入图片描述

一、 GROUP BY 用法

GROUP BY 子句用来根据一个或多个列将结果集进行分组,常与聚合函数(如 COUNT(), SUM(), AVG(), MAX(), MIN())一起使用。

SELECT column1, column2, aggregate_function(column3)
FROM table
GROUP BY column1, column2;
SELECT department, AVG(salary)
FROM employees
GROUP BY department;
-- 根据 `department` 列对 `employees` 表进行分组,然后计算每个部门的平均工资。

二、 HAVING 用法

  • HAVING 子句用于过滤 GROUP BY 生成的分组数据。
  • 它与 WHERE 子句的不同之处在于,WHERE 在分组前过滤行,HAVING 是在分组后对结果进行过滤。
SELECT column1, aggregate_function(column2)
FROM table
GROUP BY column1
HAVING aggregate_function(column2) condition;
SELECT department, AVG(salary)
FROM employees
GROUP BY department
HAVING AVG(salary) > 50000;
-- 返回平均工资大于 50000 的部门。

三、 GROUP BYHAVING 的常见踩雷点

3.1 GROUP BY 选择的列必须出现在 SELECT 中(🤣最重要的一点)

  • 使用 GROUP BY 时,SELECT 中的非聚合列必须出现在 GROUP BY 子句中,或者是聚合函数的一部分。

  • 不能在 GROUP BY 后直接选择没有参与分组或没有应用聚合函数的字段,否则 SQL 会报错。

  • 错误示例:

    SELECT department, name, AVG(salary)
    FROM employees
    GROUP BY department;
    

    name 列没有出现在 GROUP BY 中,也没有被聚合,会引发错误。

  • SQL 不知道如何处理 name,因为它没有被分组(GROUP BY 只会根据 department 分组),也没有被聚合(没有 MAX(name) 或 MIN(name))。

  • 可以去掉 name 字段,或者使用聚合函数对它进行处理。

    SELECT department, MIN(name), AVG(salary)
    FROM employees
    GROUP BY department;
    

Tips:

  • 分组后,SQL 已经将多个行数据合并为一个分组(代表一组相关的记录)

  • 这个合并的过程中,SQL 无法直接决定非分组字段应该取什么值,因为每个字段的值在一个分组中可能是不同的。Eg.如果一个部门有多个员工,你无法直接从中选择一个特定的员工姓名,因为在一个分组中,有多个员工姓名。

  • That’s why,SQL 只允许你选择分组字段或通过聚合函数“汇总”一个分组中的多个行。

来两个正确用法巩固一下脑子哈哈:
(不能在 GROUP BY 后的 SELECT 中选择没有聚合的字段,或者没有在 GROUP BY 中出现的字段!!!)

SELECT department, job_title, AVG(salary)
FROM employees
GROUP BY department, job_title;
SELECT department, job_title, MAX(employee_name), AVG(salary)
FROM employees
GROUP BY department, job_title;

3.2 GROUP BY 可以有多个列

  • 可以在 GROUP BY 中使用多个列,创建更细致的分组。

按照 departmentjob_title 进行多列分组:

SELECT department, job_title, COUNT(*)
FROM employees
GROUP BY department, job_title;

3.3 GROUP BYORDER BY 的关系

  • GROUP BY 用于分组数据,而 ORDER BY 用于排序数据。它们的顺序不一样。
  • 可以在 GROUP BY 后面使用 ORDER BY 来对结果进行排序。

按平均工资降序排序。:

SELECT department, AVG(salary)
FROM employees
GROUP BY department
ORDER BY AVG(salary) DESC;
-- 按平均工资降序排序。

3.4 聚合函数的计算顺序

  • GROUP BY 会先分组,然后应用聚合函数。如果需要在聚合函数的结果上进一步过滤数据,应该使用 HAVING 而不是 WHERE

    SELECT department, SUM(salary)
    FROM employees
    WHERE hire_date > '2020-01-01'   -- WHERE 在聚合之前
    GROUP BY department;
    

3.5 HAVING 中的聚合函数和常量比较

  • HAVING 子句中,通常会看到聚合函数与某个常量进行比较。这样做没有问题,但必须要确保聚合函数的语法正确。

    SELECT department, COUNT(*)
    FROM employees
    GROUP BY department
    HAVING COUNT(*) > 10;  -- 这个是正确的
    

3.6 避免在 HAVING 中做不必要的计算

  • 不要在 HAVING 中做不必要的计算,可能会导致性能下降。如果能在 WHERE 中提前过滤,就避免使用 HAVING

    SELECT department, SUM(salary)
    FROM employees
    WHERE salary > 50000    -- 提前过滤
    GROUP BY department;
    

各位看客老爷 万福金安🤣一键三连呀🤣🤣🤣

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

喻师傅

谢谢您!我会继续努力创作!

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值