SUM(DISTINCT(列))在某些条件下给出错误的结果

时间:2013-09-21 22:32:02

标签: mysql sql database

此查询

SELECT u.username, 
SUM(p.likes) AS likePoints1, 
SUM(p2.likes)*2 AS likePoints2 
FROM users as u 
LEFT JOIN (SELECT recommendedByUserId as rid, id as ruid from users WHERE created >= DATE('2013-09-16') AND created <= DATE('2013-09-30')) AS r ON r.rid = u.id 
LEFT JOIN (SELECT * FROM posts WHERE created >= DATE('2013-09-16') AND created <= DATE('2013-09-30')) AS p ON p.author_id = ruid 
LEFT JOIN (SELECT * FROM posts WHERE created >= DATE('2013-09-16') AND created <= DATE('2013-09-30')) AS p2 ON p2.author_id = u.id 
GROUP BY u.id 

在“likePoints2”列上显示错误的结果

SELECT u.username, 
SUM(p2.likes)*2 AS likePoints2 
FROM users as u 
LEFT JOIN (SELECT * FROM posts WHERE created >= DATE('2013-09-16') AND created <= DATE('2013-09-30')) AS p2 ON p2.author_id = u.id 
GROUP BY u.id 

完全正确。

问题是,我需要总结posts.author_id =当前u.id在给定日期范围内的所有posts.likes。

我很感激任何意见!

测试数据

USERS

id | recommendedByUserId
1  | 3
2  | 3
3  | NULL
4  | 1

帖子

author_id | likes
1         | 5
3         | 2
4         | 1

所以在上面的例子中,结果应该是:

userid | recommPoints | likePoints1 | likePoints2
1      | 10           | 1           | 10
2      | NULL         | NULL        | NULL
3      | 20           | 5           | 4
4      | NULL         | NULL        | 2

1 个答案:

答案 0 :(得分:2)

基本问题是每个连接为连接的值添加多行。所以你最终会多次计算东西。解决它的一般方法是使每个单独的分组成为单独的子选择。您可以将其中一个作为主选择的一部分。

诊断这些问题的一个好方法是删除组,然后查看基础数据集。使用where子句限制为不起作用的已知案例。

Select
    u.username, 
    p1.likePoints1, 
    p1.recommPoints,
    Sum(p2.likes) * 2 As likePoints2 -- assume the *2 is part of the algorithm
From
    users u
        Left Outer Join (
            Select
                r.recommendedByUserId rid,
                Sum(p.likes) AS likePoints1,
                Count(Distinct r.id) * 10 As recommPoints
            From
                users r
                    Left Outer Join
                posts p
                    On r.id = p.author_id And 
                       p.created >= Date('2013-09-16') And
                       p.created <= Date('2013-09-30')
            Where
                r.created >= Date('2013-09-16') And 
                r.created <= Date('2013-09-30')
            Group By
                r.recommendedByUserId
    ) p1
        on u.id = p1.rid
        Left Outer Join
    posts p2
        On p2.author_id = u.id And
           p2.created >= Date('2013-09-16') And
           p2.created <= Date('2013-09-30')
Group By
    u.username,
    p1.likePoints1,
    p1.recommPoints

缩减 Example Fiddle