Задать вопрос
Shultc
@Shultc
RnD Developer

Как в SQL убрать подзапросы в BETWEEN?

Есть значит у меня SELECT довольно нагруженный. Хотелось бы его облегчить, хотя бы убрав подзапросы. Над чем я больше всего ломаю голову, так это подзапросы в BETWEEN. Сейчас часть с BETWEEN выглядит так:
...
SELECT * FROM Visitors v
WHERE v.last_visit_time BETWEEN
    (SELECT start_time FROM Event WHERE event_id = @first_event) AND
    (SELECT start_time FROM Event WHERE event_id = @second_event) AND
...

То есть, в данном случае, меня интересуют все посетители, которые последний раз посещали нас между двумя определёнными событиями. Есть ли способ избавиться от этих подзапросов? Без них работает на порядок быстрее, но хочется всё-таки делать всё за один раз.

И, как бонус, как можно отсюда убрать подзапрос:
...
AND g.place_id IN (SELECT place_id FROM Event WHERE event_id = @first_event)
...

Все предоставленные запросы являются клонами настоящих. Ни одна корпорация не пострадала от утечки данных при задавании этого вопроса.
  • Вопрос задан
  • 3104 просмотра
Подписаться 4 Оценить Комментировать
Решения вопроса 2
Rsa97
@Rsa97
Для правильного вопроса надо знать половину ответа
А что мешает заранее получить нужные значения start_time там же, где устанавливаются переменные @first_event и @second_event? С place_id не совсем понятно, сколько может быть событий с одним event_id? Если только одно - то тоже получать заранее.
Ответ написан
@IgoNsk
backend web developer
Мне кажется проблема здесь в использовании переменных @first_start_time, @second_start_time . Если в запросе используются переменные, то его результаты не кешируются на уровне MySQL. Если во вложенном запросе нет никаких условий, связывающих его с внешним запросом, то результат его выполнения кешируется, иначе вычисляется для каждой строки заново.

Ну и почти любой подзапрос можно переписать в виде JOIN, только даст ли это выигрыш по производительности. Ибо мне кажется затык в переменных.

Подзапрос можно убрать так
from
 ...
 join Event as FirstEvent
   on FirstEvent.place_id = g.place_id

 where
 ..
 and FirstEvent.event_id = @first_event
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

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

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