Этот ответ я изначально пытался опубликовать на удаленный вопрос, который не указывал на проблему с MySQL. Я все еще продолжу и использую SQL Server для рефакторинга запроса с использованием CTE, а затем преобразую обратно во вложенные запросы (если они есть). Извините за форматирование, Джефф Этвуд прислал мне исходный текст, и мне пришлось переформатировать его снова.
Трудно обойтись без данных, ожидаемых результатов и хороших имен, но я бы преобразовал все вложенные запросы в CTE, сложил их, назови их осмысленно и произвел рефакторинг - начиная с исключения столбцов, которые вы не используете. Удаление столбцов не приведет к улучшению, потому что оптимизатор довольно умен, но он даст вам возможность улучшить ваш запрос - возможно, с учетом некоторых или всех CTE. Я не уверен, что делает ваш код, но вы можете найти полезными новые функции типа RANK (), потому что кажется, что вы используете шаблон поиска с поиском со всеми этими самостоятельными соединениями.
Так что начните отсюда. Я рассмотрел улучшения e7 для вас, столбцы, неиспользуемые из e7, могут указывать либо на дефект, либо на неполное представление о возможностях группировки, но если эти столбцы действительно не нужны, то это может просочиться через всю вашу логику в e6, е5 и е3. Если группировка в e7 верна, вы можете исключить все, кроме max (id) в результатах и объединении. Я не понимаю, почему у вас должно быть несколько MAX (id) для каждой категории, потому что это умножит ваши результаты при присоединении, поэтому MAX (id) должен быть уникальным в пределах категории, и в этом случае категория является избыточной в объединении.
WITH e3 AS (
select min(e1.rank) as rank,
e1.entity,
e1.provider_id,
e1.service_date
from table_a e1
where e1.site_id is not null
group by e1.entity, e1.provider_id, e1.service_date
)
,e5 AS (
select max(e2.id) as id,
e3.rank,
e2.entity,
e2.provider_id,
e2.service_date
from table_a e2
inner join e3
on e2.rank= e3.rank
and e2.entity = e3.entity
and e2.provider_id = e3.provider_id
and e2.service_date = e3.service_date
and e2.rank= e3.rank
group by e2.entity, e2.provider_id, e2.service_date, e3.rank
)
,e6 AS (
select e4.* -- switch from * to only the columns you are actually using
from table_a e4
inner join e5
on e4.id = e5.id
and e4.rank= e5.rank
)
,e7 AS (
select max(e6.id) as id, e6.category -- unused, e6.entity, e6.service_date
from e6
group by e6.category, e6.entity, e6.service_date
-- This instead
-- select max(e6.id) as id
-- from e6
-- group by e6.category, e6.entity, e6.service_date
)
select e8.*
from table_a e8
inner join e7
on e8.id = e7.id
and e7.category = e8.category
-- THIS INSTEAD on e8.id = e7.id