SQL: подсчет уникальных голосов с ограничением количества голосов в час - PullRequest
3 голосов
/ 16 сентября 2008

С учетом таблицы голосов (пользователи голосуют за выбор и должны указать адрес электронной почты):

votes
--
id: int
choice: int
timestamp: timestamp
ip: varchar
email: varchar

Каков наилучший способ подсчета «уникальных» голосов (пользователь представляет собой уникальную комбинацию электронной почты + ip), учитывая ограничение, которое они могут голосовать только дважды в час?

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

Я понимаю, что анонимное онлайн-голосование изначально ошибочно, но я не уверен, как это сделать с SQL. Должен ли я использовать внешний скрипт или что-то вместо этого? (Для каждого варианта, для каждой пары email + ip, получите голос, вычислите следующую + 1ч метку времени, посчитайте / отмените / подсчитайте голоса, перейдите к следующему часу и т. Д.)

Ответы [ 3 ]

3 голосов
/ 16 сентября 2008

Что-то вроде

select email, ip, count(choice)
from votes
group by email, ip, datepart(hour, timestamp)

Если я правильно понимаю

0 голосов
/ 16 сентября 2008

Я думаю, что это сделало бы:

SELECT choice, count(*) 
FROM votes v 
WHERE 
  ( SELECT count(*) 
    FROM   votes v2
    WHERE  v.email = v2.email 
    AND    v.ip    = v2.ip 
    AND    v2.timestamp BETWEEN dateadd(hour, -1, v.timestamp) AND v.timestamp 
  ) < 2 

К вашему сведению, для подсчета голосов, когда пользователи могут голосовать только один раз в час, мы можем сделать это:

SELECT choice, count(*) 
FROM votes v 
WHERE NOT EXTISTS 
  ( SELECT * 
    FROM   votes v2
    WHERE  v.email = v2.email 
    AND    v.ip    = v2.ip 
    AND    v2.timestamp BETWEEN dateadd(h,v.timestamp,-1) AND v.timestamp 
  ) 
0 голосов
/ 16 сентября 2008

Вы можете переписать свой оператор вставки, чтобы разрешить вставку только голосов на основании ваших противопоставлений:

Insert Into Votes
(Choice, Timestamp, IP, Email)
Select
Top 1
@Choice, @Timestamp, @IP, @Email
From
Votes
Where
(Select Count(*) From Votes Where
    IP = @IP
    and Email = @Email
    and Timestamp > DateAdd(h, -2, GetDate())) < 3

Вы не упомянули, какой язык SQL вы использовали, так что это в SQL Server 2005.

...