2013-10-25 3 views
0

У меня есть следующий запрос, гдеMySQL LEFT JOIN оптимизации

  • А имеет 1 000 000 строк
  • В, С, D имеет 150 000 строк каждая
  • Е имеет 50 000 строк

Выполнение запроса, по-видимому, занимает около 50 секунд. Обычно он содержит предложение WHERE, поскольку он выполняет поиск по всем возможным данным в базе данных. Можно ли улучшить это?

SELECT A.one, A.two, A.three 
FROM A 
LEFT JOIN B ON (A.id = B.id) 
LEFT JOIN C ON (A.id = C.d) 
LEFT JOIN D ON (A.id = D.id) 
LEFT JOIN E ON (A.name = E.name 
AND E.date <= A.date) 
ORDER BY A.id ASC 

Объяснить запрос:

+----+-------------+-------+--------+---------------+----------+---------+-----------+--------+-------------+ 
| id | select_type | table | type | possible_keys | key  | key_len | ref  | rows | Extra  | 
+----+-------------+-------+--------+---------------+----------+---------+-----------+--------+-------------+ 
| 1 | SIMPLE  | A  | index | NULL   | PRIMARY | 17  | NULL  | 357752 |    | 
| 1 | SIMPLE  | B  | eq_ref | PRIMARY  | PRIMARY | 17  | db.A.id |  1 | Using index | 
| 1 | SIMPLE  | C  | eq_ref | PRIMARY  | PRIMARY | 17  | db.A.id |  1 | Using index | 
| 1 | SIMPLE  | D  | eq_ref | PRIMARY  | PRIMARY | 17  | db.A.id |  1 | Using index | 
| 1 | SIMPLE  | E  | ref | Name,Date  | Name  | 62  | db.A.name |  1 |    | 
+----+-------------+-------+--------+---------------+----------+---------+-----------+--------+-------------+ 
+0

Какое предложение WHERE обычно содержит? И - сколько строк вы ожидаете, что каждый из B, C, D и E должен иметь * для каждой строки A *? – ruakh

+0

Можете ли вы попытаться присоединиться только к таблицам A и E и посмотреть, сколько времени потребуется? Возможно, совпадение строк замедляет работу. – Atle

ответ

1

я бы рекомендовал заменить индексы, которые вы имеете на E - Name и Date с индексом двойного столбца на обоих, потому что в прошлом присоединиться, вы эффективно от E, где name и date соответствуют критериям. Поскольку name является eq, он должен быть первым в индексе.

ALTER TABLE `E` ADD INDEX idx_join_optimise (`name`,`date`) 

Это позволит полностью выбрать индекс.

Кроме того - я предполагаю, что это пример запроса, но вы, кажется, не используете B, C или D, что возможно замедляет его.

Если предложение WHERE что вы упомянули используются значения из других таблиц, я бы предположить, изменяя их в INNER JOIN на основании критерия .. (Было бы полезно, если вы вывесили несколько примеров того, что вы делали)