在 SQL 中,HAVING 子句通常用于对“分组后的结果”进行筛选,而不是对原始行进行筛选。
换句话说:WHERE 过滤行,HAVING 过滤组。
下面详细说明什么场景需要用 HAVING。
当你使用了 GROUP BY,并且想根据统计结果(如总数、平均值、最大值等)来筛选分组时,必须用 HAVING。
示例:查询订单数大于 3 的客户
SELECT customer_id, COUNT(*) AS order_count
FROM orders
GROUP BY customer_id
HAVING COUNT(*) > 3;
❌ 下面这样是错误的:
WHERE COUNT(*) > 3 -- 非法,WHERE 中不能使用聚合函数
例如:
SELECT class_id, AVG(score) AS avg_score
FROM student
GROUP BY class_id
HAVING AVG(score) > 60;
HAVING 中可以使用多个聚合条件:
SELECT product_id,
SUM(quantity) AS total_qty,
AVG(price) AS avg_price
FROM sales
GROUP BY product_id
HAVING SUM(quantity) > 100
AND AVG(price) < 50;
| 对比项 | WHERE | HAVING |
|---|---|---|
| 作用对象 | 原始行 | 分组后的结果 |
| 是否可用聚合函数 | ❌ 不可以 | ✅ 可以 |
| 执行顺序 | 先执行 | 后执行 |
正确执行顺序:
FROM → WHERE → GROUP BY → HAVING → SELECT → ORDER BY
先过滤数据,再分组,再筛组:
SELECT user_id, COUNT(*) AS login_count
FROM login_log
WHERE login_time >= '2024-01-01'
GROUP BY user_id
HAVING COUNT(*) >= 10;
❌ 如果只是过滤单行数据:
SELECT * FROM user WHERE age > 18;
→ 用 WHERE 即可,不需要 HAVING
只要筛选条件涉及“分组后的统计结果”,就必须用 HAVING。
如果你愿意,我也可以结合你具体的业务表结构,帮你写更贴合的 SQL 示例。
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。