@daMage

Почему запрос так долго выполняется?

Есть 3 таблицы: keywords, images, images_keywords

SELECT SQL_NO_CACHE *
FROM keywords
JOIN(
	SELECT DISTINCT keywords.id
	FROM keywords
	JOIN images_keywords ON keywords.id = keyword_id
	JOIN images ON image_id = images.id WHERE images.space = 1
) as ids ON keywords.id = ids.id

Кто может обяснить, почему этот запрос выполняется 1.6с? Подзапрос возвращает ~800 id за 0.0004с, а количество записей в таблице keywords ~1000.

a598f6166e2b4842973d35ebe73f6fe9.png
К сожалению, не сильно понимаю, что означают данные из explain. Вижу temporary table, вроде бы плохо, но это данные подзапроса, который выполняется мгновенно.
  • Вопрос задан
  • 313 просмотров
Пригласить эксперта
Ответы на вопрос 3
@dmitryKovalskiy
программист средней руки
Я вообще не понимаю зачем построен такой запрос.
Почему просто не
SELECT k.* --Или лучше перечислить столбцы для выборки
  FROM keywords as k
  JOIN images_keywords ON keywords.id = keyword_id
  JOIN images ON image_id = images.id WHERE images.space = 1
Ответ написан
Melkij
@Melkij
PostgreSQL DBA
SELECT DISTINCT keywords.id
  FROM keywords
  JOIN images_keywords ON keywords.id = keyword_id
  JOIN images ON image_id = images.id WHERE images.space = 1

С какой целью вы вообще в этом подзапросе джойните таблицу keywords?
SELECT DISTINCT keyword_id
  FROM images_keywords
  JOIN images ON image_id = images.id WHERE images.space = 1

Тот же самый результат будет.

Вообще, джойн с подзапросом вам и не нужен
SELECT SQL_NO_CACHE *
FROM keywords
WHERE keywords.id IN (
  SELECT DISTINCT keyword_id
  FROM images_keywords
  JOIN images ON image_id = images.id WHERE images.space = 1
)

Для mysql актуальных версий in subquery должен работать адекватно.
Ответ написан
VladimirAndreev
@VladimirAndreev
php web dev
м..

SELECT t.*
FROM keywords t
WHERE 1=1
    AND EXISTS( SELECT a.id FROM images_keywords a WHERE t.id = a.keyword_id )
    AND EXISTS( SELECT b.id FROM images b WHERE b.id = t.image_id and b.space =1 )
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы