Все ответы не достигли ключевой точки.
Предположим, у нас есть таблица:
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 строк с идентификатором и значением от 1 до 10:
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);
Попробуйте выполнить следующие 2 запроса:
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.
Вот разница:
SELECT `value` v FROM `table` WHERE `v`>5;
Ошибка # 1054 - неизвестный столбец 'v' в 'предложении where'
SELECT `value` v FROM `table` HAVING `v`>5; -- Get 5 rows
Предложение WHERE позволяет условию использовать любой столбец таблицы, но не может использовать псевдонимы или статистические функции.
Предложение HAVING позволяет условию использовать выбранный (!) Столбец, псевдоним или статистическую функцию.
Это потому, что предложение WHERE фильтрует данные перед выбором, а предложение HAVING фильтрует результирующие данные после выбора.
Поэтому условия в выражении WHERE будут более эффективными, если в таблице много строк.
Попробуйте EXPLAIN, чтобы увидеть разницу:
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 |
+----+-------------+-------+-------+---------------+-------+---------+------+------+-------------+
Вы можете видеть, ГДЕ или HAVING использует индекс, но строки отличаются.