Распределение забавным запроса седе


Есть 1-ко-многим связь между постами стол и голосами стол, и они вступают на должности.ИД = голосов.сообщения дан. Я хотел бы знать, сколько постов у 1, 2, 3, 5 и т. д. голосов.

Благодаря вафля самых противоречивых постов запросов, это было тривиально, чтобы написать это:

declare @VoteStats table (PostId int, up int) 

set nocount on

insert @VoteStats
select
    PostId, 
    up = sum(case when VoteTypeId = 2 then 1 else 0 end)
from Votes
where VoteTypeId in (2,3)
group by PostId

set nocount off

select up, count(*)
from @VoteStats
group by up;

Однако, это выполняется в полном объеме 22 секунд на переполнение стека данных дампа.

Я с видом очевидный способ ускорить этот запрос, возможно, избегая создания таблицы VoteStats?



188
3
задан 7 сентября 2011 в 09:09 Источник Поделиться
Комментарии
2 ответа

Не Создание таблицы VoteStats делает большой разницы. Получает его вниз до ~5.5 секунд.

set nocount on

select up, count(*)
from (
select
PostId,
up = sum(case when VoteTypeId = 2 then 1 else 0 end)
from Votes
where VoteTypeId in (2,3)
group by PostId
) a
group by up
order by up

http://data.stackexchange.com/stackoverflow/q/112108/

Из плана выполнения таблицы переменных версии, похоже, что сканирование таблицы и отсортировать это довольно дорого.

2
ответ дан 8 сентября 2011 в 09:09 Источник Поделиться

Я думаю, что это должно быть быстрее, потому что вместо подведения итогов 1 за каждый голос, который имеет VoteTypeId=2, я подсчет голосов с VoteTypeId=2:

with VoteCountsByPost as
(
select
p.Id as PostId,
count(v.Id) as up
from Posts p
left join Votes v on v.PostId = p.Id and v.VoteTypeId = 2
group by p.Id
)
select up, count(*)
from VoteCountsByPost
group by up
order by up

Также, обратите внимание, что результаты немного отличаются: Вы запрос не принимает во внимание, что посты не имеют никакого голоса.

Например, если пост имеет право голоса с VoteTypeId != 2, тогда этот пост будет отображаться с 0 ИБП. Если он не имеет никакого голоса, тогда этот пост будет полностью исключаются из результирующего набора.

Я не знаю, если это задуманное поведение.

2
ответ дан 8 сентября 2011 в 10:09 Источник Поделиться