您好所有,并在此先感谢 我有表accounts
,votes
和contests
一票由一个作者ID,赢家ID,和比赛的ID,以便停止人们投票两次
编号喜欢为任何给定的帐户显示,多少次他们赢得了比赛,多少次他们第二次和多少次他们来第三
什么是最快(执行时间)的方式来做到这一点? (即时通讯使用MySQL)SQL获取指定的用户投票中获胜
回答
长时间使用MySQL后,我得出的结论是,实际上任何对GROUP BY的使用对于性能都非常不利,所以这里有一些临时表的解决方案。
CREATE TEMPORARY TABLE VoteCounts (
accountid INT,
contestid INT,
votecount INT DEFAULT 0
);
INSERT INTO VoteCounts (accountid, contestid)
SELECT DISTINCT v2.accountid, v2.contestid
FROM votes v1 JOIN votes v2 USING (contestid)
WHERE v1.accountid = ?; -- the given account
请确保您有一个索引votes(accountid, contestid)
。
现在您已经有了您的给定用户所参加的每场比赛的表格,以及参加过相同比赛的所有其他帐户。
UPDATE Votes AS v JOIN VoteCounts AS vc USING (accountid, contestid)
SET vc.votecount = vc.votecount+1;
现在,您在每次比赛中获得每个帐户的投票数。
CREATE TEMPORARY TABLE Placings (
accountid INT,
contestid INT,
placing INT
);
SET @prevcontest := 0;
SET @placing := 0;
INSERT INTO Placings (accountid, placing, contestid)
SELECT accountid,
IF([email protected], @placing:[email protected]+1, @placing:=1) AS placing,
@prevcontest:=contestid AS contestid
FROM VoteCounts
ORDER BY contestid, votecount DESC;
现在你有一张桌子,每个帐户都与他们各自在每个比赛中的位置配对。这很容易得到计数对于给定的配售:
SELECT accountid, COUNT(*) AS count_first_place
FROM Placings
WHERE accountid = ? AND placing = 1;
你也可以使用MySQL招做一个所有三个查询。一个布尔表达式总是在MySQL中返回一个整数值0或1,所以你可以使用SUM()
来计算1。
SELECT accountid,
SUM(placing=1) AS count_first_place,
SUM(placing=2) AS count_second_place,
SUM(placing=3) AS count_third_place
FROM Placings
WHERE accountid = ?; -- the given account
回复您的评论:
是的,这是一个复杂的任务,无论从你你想要的结果的归一化数据去的地方。您希望将其汇总(汇总),排名并再次汇总(计数)。这是一堆工作! :-)
此外,单个查询并不总是执行给定任务的最快方式。在程序员中,一个常见的误解是,较短的代码隐式地加快了代码的速度。
注意我没有测试过,所以你的里程可能会有所不同。
重新您有关更新的问题:
这让每个帐户票COUNT()
没有使用GROUP BY的一个取巧的方法。我已经添加了表别名v和vc,所以现在可能会更清楚。在votes
表中,给定帐户/比赛有N行。在votescount
表中,每个帐户/比赛有一行。当我加入时,UPDATE是针对N行进行评估的,所以如果我为这N行中的每一行加1,那么我在每个相应帐户/竞赛对应的行中获得存储在votescount
中的N的计数。
如果我正确解释事情,阻止人们投票两次我认为你只需要在作者(账户?)ID和contestID的投票表上唯一的索引。它不会阻止人们拥有多个帐户和两次投票,但它会阻止任何人在同一个帐户的两次比赛中投票。为了防止欺诈(袜子傀儡帐户),您需要检查投票模式,并检测帐户何时投票更频繁,然后统计可能。除非你有很多比赛可能很难。
是啊我已经让他们索引的作者和比赛谢谢:)对帐单的巨大感激,生病尝试在一秒内出 – Pez 2010-06-23 12:25:05
- 1. 在同一个查询中获取用户群投票的平均数和个人用户的投票数?
- 2. Laravel投票系统获取用户选择的项目数
- 3. 从Facebook获取投票结果图Graph
- 4. 如何在投票中注册用户的投票?
- 5. 如何获取在AccessDecisionVoter投票方法实现中获取的url?
- 6. Django:确定用户是否投了票
- 7. 如何在Ruby on Rails中获取未投票的帖子数
- 8. 验证用户投票的投票一次
- 9. PHP投票 - 跟踪用户
- 10. 获取门票
- 11. 获取检票
- 12. 如何在用户投票后禁用(相应)投票按钮?
- 13. 获取每个客户的总发票
- 14. 获取完整的特定指数的股票列表
- 15. 如何在投票后将用户重定向到投票页面?
- 16. 获取当前投票等级的快速方法?
- 17. 获取股票图
- 18. 投票与长投票
- 19. SQL查询来获取“投得分”
- 20. 投票 - 票数与投票率?
- 21. 获取的用户从指针(Parse.com)
- 22. 从SQL Server中获取unix用户
- 23. Ruby on Rails - 每月顶级投票获取者
- 24. 独特的男女投票谁投票
- 25. 从另一个获胜形式调用一个获胜形式
- 26. 为特定帖子创建投票投票WordPress的
- 27. 获取用户时获取用户组
- 28. 获取特定用户
- 29. 的Rails充当可投票检查,如果用户登录到投票
- 30. SQL计算获胜和连败记录
您应该添加3个表格的确切方案。这样可以更轻松地帮助完成所需的查询。例如,不清楚获胜者是否保存在比赛表中,或者只能由选票决定。 – 2010-06-23 11:58:27
我可能会考虑将获胜者存储在“比赛”表中并定期更新,但现在我只想知道用户是第一,第二和第三次(纯粹通过计票)确定的次数 – Pez 2010-06-23 12:39:00