我正在开发一个论坛系统(mysql),我不确定在单个查询帖子,上下投票以及当前用户是否为每个帖子投票时,选择哪条路径可以获得更好的性能。 第一个选项是:
SELECT posts.post_id, post_content, display_name,
(SELECT COUNT(post_id) FROM post_votes WHERE post_votes.post_id=posts.post_id AND post_votes.user_id='+user_id+') voted,
(SELECT COUNT(post_id) FROM post_votes WHERE post_votes.post_id=posts.post_id AND up_vote=1) upvotes,
(SELECT COUNT(post_id) FROM post_votes WHERE post_votes.post_id=posts.post_id AND up_vote=0) downvotes
FROM posts JOIN users ON users.user_id=posts.user_id WHERE parent_id ='+parent_id+' ORDER BY post_id DESC
第二个选项是用LEFT JOIN和count替换所有count子查询。 一种方法对另一种方法有什么好处吗?
修改
由于我希望检索所有帖子而不是一个对帖子进行分组的行,我想出了这个查询(带有一些灵感from here):
SELECT p.post_id, post_content, display_name,
COALESCE(v.upvotes, 0) AS upvotes,
COALESCE(v.downvotes, 0) AS downvotes,
COALESCE(v.voted, 0) AS voted
FROM posts p
LEFT JOIN (
SELECT post_id,
SUM(vt.up_vote = 1) AS upvotes,
SUM(vt.up_vote = 0) AS downvotes,
MAX(IF(vt.user_id = ' + user_id + ', vt.up_vote, NULL)) voted
FROM post_votes vt
GROUP BY vt.post_id
)
v ON v.post_id = p.post_id
JOIN users ON users.user_id=p.user_id
WHERE parent_id =' + parent_id + ' ORDER BY post_id DESC
我已经在我的演示数据库上运行了两个解决方案(目前很小,每个表中包含不到100行),持续时间相同。 问题是从长远来看哪一个会更快。
答案 0 :(得分:2)
我很难想到子查询比连接更快的地方。
在这种情况下,您甚至不需要加入。在一个查询中完成所有操作:
SELECT
p.post_id,
p.post_content,
u.display_name,
COUNT(pv.post_id) AS voted,
SUM(pv.up_vote = 1) AS upvotes,
SUM(pv.up_vote = 0) downvotes
FROM posts p
JOIN users u ON u.user_id = p.user_id
LEFT JOIN post_votes pv ON posts.post_id = pv.post_id AND pv.user_id ='whatever'
WHERE p.parent_id ='+parent_id+'
GROUP BY p.post_id
ORDER BY p.post_id DESC
pv.up_vote = 'whatever'
函数内的SUM()
返回true或false,1或0.这就是我们在这里使用SUM()
函数的原因。瞧,一切都在一个查询中。