首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >WHERE vs HAVING

WHERE vs HAVING
EN

Stack Overflow用户
提问于 2010-05-25 21:57:42
回答 7查看 205.3K关注 0票数 259

为什么需要将自己创建的列(例如select 1 as "number")放在HAVING之后,而不是MySQL中的WHERE

WHERE 1代替(编写整个定义而不是列名)有什么缺点吗?

EN

回答 7

Stack Overflow用户

回答已采纳

发布于 2010-05-25 21:59:46

为什么需要将自己创建的列(例如"select 1 as number")放在MySQL中的WHERE之后,而不是放在哪里?

WHEREGROUP BY之前应用,HAVING在之后应用(并且可以过滤聚合)。

通常,您不能在这两个子句中引用别名,但MySQL允许在GROUP BYORDER BYHAVING中引用SELECT级别名。

是否有任何缺点而不是执行"WHERE 1“(编写整个定义而不是列名)

如果计算表达式不包含任何聚合,则将其放入WHERE子句很可能会更有效。

票数 332
EN

Stack Overflow用户

发布于 2013-09-10 12:30:36

关于这个问题的所有其他答案都没有击中关键点。

假设我们有一个表:

代码语言:javascript
复制
CREATE TABLE `table` (
 `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
 `value` int(10) unsigned NOT NULL,
 PRIMARY KEY (`id`),
 KEY `value` (`value`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8

并且有10行,id和值都在1到10之间:

代码语言:javascript
复制
INSERT INTO `table`(`id`, `value`) VALUES (1, 1),(2, 2),(3, 3),(4, 4),(5, 5),(6, 6),(7, 7),(8, 8),(9, 9),(10, 10);

尝试以下两个查询:

代码语言:javascript
复制
SELECT `value` v FROM `table` WHERE `value`>5; -- Get 5 rows
SELECT `value` v FROM `table` HAVING `value`>5; -- Get 5 rows

您将得到完全相同的结果,您可以看到HAVING子句可以在没有GROUP BY子句的情况下工作。

不同之处在于:

代码语言:javascript
复制
SELECT `value` v FROM `table` WHERE `v`>5;

上述查询将引发错误: Error #1054 -where子句中未知列'v‘

代码语言:javascript
复制
SELECT `value` v FROM `table` HAVING `v`>5; -- Get 5 rows

WHERE子句允许条件使用任何表列,但不能使用别名或聚合函数。HAVING子句允许条件使用选定的(!)列、别名或聚合函数。

这是因为WHERE HAVING 子句在select之前过滤数据,而子句在select之后过滤结果数据。

因此,如果一个表中有很多行,那么将条件放在WHERE子句中会更有效率。

试试EXPLAIN看看其中的关键区别:

代码语言:javascript
复制
EXPLAIN SELECT `value` v FROM `table` WHERE `value`>5;
+----+-------------+-------+-------+---------------+-------+---------+------+------+--------------------------+
| id | select_type | table | type  | possible_keys | key   | key_len | ref  | rows | Extra                    |
+----+-------------+-------+-------+---------------+-------+---------+------+------+--------------------------+
|  1 | SIMPLE      | table | range | value         | value | 4       | NULL |    5 | Using where; Using index |
+----+-------------+-------+-------+---------------+-------+---------+------+------+--------------------------+

EXPLAIN SELECT `value` v FROM `table` having `value`>5;
+----+-------------+-------+-------+---------------+-------+---------+------+------+-------------+
| id | select_type | table | type  | possible_keys | key   | key_len | ref  | rows | Extra       |
+----+-------------+-------+-------+---------------+-------+---------+------+------+-------------+
|  1 | SIMPLE      | table | index | NULL          | value | 4       | NULL |   10 | Using index |
+----+-------------+-------+-------+---------------+-------+---------+------+------+-------------+

您可以看到WHEREHAVING使用索引,但是行是不同的。

票数 318
EN

Stack Overflow用户

发布于 2010-05-25 22:00:56

主要区别在于WHERE不能用于分组项(如SUM(number)),而HAVING可以。

原因是WHERE是在分组之前完成的,HAVING是在分组完成之后完成的。

票数 64
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/2905292

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档