编程SQL 分析师

解释 SQL 中 HAVING 和 WHERE 之间的区别。每个的用途是什么,它们如何与聚合函数交互,以及如何避免使用过程中的常见错误?

用 Hintsage AI 助手通过面试

答复

WHERE 在执行分组和聚合之前过滤行,即确定哪些记录将进入分组/聚合。HAVING 在应用聚合函数后过滤分组。

  • WHERE:不能使用聚合函数(SUM, AVG 等),因为过滤在分组之前发生。
  • HAVING:可以使用聚合函数,因为过滤在分组之后发生。

示例:

-- 获取总薪资超过 50000 的部门,排除已离职员工 SELECT department, SUM(salary) as total FROM employees WHERE status = 'active' GROUP BY department HAVING SUM(salary) > 50000;

这里:

  • WHERE status = 'active' — 在计算部门的总薪资之前排除了已离职员工;
  • HAVING SUM(salary) > 50000 — 只显示总薪资超过 50000 的部门。

有陷阱的问题

可以在 WHERE 中使用聚合函数吗?

错误:试图写 WHERE SUM(amount) > 100,但这是不可以的 — 聚合函数只能在 HAVING 中使用。

示例(错误):

SELECT customer_id, SUM(amount) FROM orders WHERE SUM(amount) > 100 GROUP BY customer_id -- 错误:在 WHERE 中错误使用 SUM()

正确:

SELECT customer_id, SUM(amount) FROM orders GROUP BY customer_id HAVING SUM(amount) > 100;

由于对主题细微差别的不熟悉而导致的实际错误示例


故事

CRM 开发。在 WHERE 中尝试通过 COUNT(order_id) > 5 来过滤订单数量 >5 的客户,查询无法执行。结果:由于不能在 WHERE 中使用 COUNT,客户数量不正确。


故事

商业分析。在 WHERE 中筛选不活跃商品时使用了 HAVING。结果:导致了“空”组的聚合和缓慢的 SQL。通过将状态筛选移至 WHERE 进行修正。


故事

复杂报告。在没有 GROUP BY 的情况下使用 HAVING 来过滤单独行。在某些数据库中会导致错误,在其他数据库中会导致不明确的行为。结论:HAVING 必须在分组之后,并用于聚合条件。