У меня есть таблица со столбцами:
CREATE TABLE aggregates (
a VARHCAR,
b VARCHAR,
c VARCHAR,
metric INT
KEY test (a, b, c, metric)
);
Если я сделаю запрос вроде:
SELECT b, c, SUM(metric) metric
FROM aggregates
WHERE a IN ('a', 'couple', 'of', 'values')
GROUP BY b, c
ORDER BY b, c
Запрос занимает 10 секунд, объяснение:
+----+-------------+------------+-------+---------------+------+---------+------+--------+-----------------------------------------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+------------+-------+---------------+------+---------+------+--------+-----------------------------------------------------------+
| 1 | SIMPLE | aggregates | range | test | test | 767 | NULL | 582383 | Using where; Using index; Using temporary; Using filesort |
+----+-------------+------------+-------+---------------+------+---------+------+--------+-----------------------------------------------------------+
Если я также сгруппирую / упорядочить по столбцу a, то мне не понадобится временная / файловая сортировка, но я сам сделаю то же самое в другом запросе:
SELECT b, c, SUM(metric) metric
FROM (
SELECT a, b, c, SUM(metric) metric
FROM aggregates
WHERE a IN ('a', 'couple', 'of', 'values')
GROUP BY a, b, c
ORDER BY a, b, c
) t
GROUP BY b, c
ORDER BY b, c
Запрос занимает 1 секунду, а объяснение таково:
+----+-------------+------------+-------+---------------+------+---------+------+--------+---------------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+------------+-------+---------------+------+---------+------+--------+---------------------------------+
| 1 | PRIMARY | <derived2> | ALL | NULL | NULL | NULL | NULL | 252 | Using temporary; Using filesort |
| 2 | DERIVED | aggregates | range | test | test | 767 | NULL | 582383 | Using where; Using index |
+----+-------------+------------+-------+---------------+------+---------+------+--------+---------------------------------+
Почему это? Почему быстрее, если я делаю группировку в отдельном внешнем запросе, а не просто делаю все в одном?