我试图在MySQL查询中获得两个不同表的行数和两个LEFT JOIN
。当我在一张桌子上有一个像这样的COUNT
时效果很好:
SELECT a.title, a.image, COUNT(o.id) AS occasions
FROM activity a
LEFT JOIN occasion AS o ON a.id = o.activity_id
WHERE a.user_id = 1
GROUP BY a.id
ORDER BY a.created_at
DESC LIMIT 50
在这里,一切正常,我得到了很多“场合”。
但是当我尝试添加额外的COUNT
和额外的LEFT JOIN
时,第二个COUNT
的结果是错误的:
SELECT a.title, a.image, COUNT(o.id) AS occasions, COUNT(au.id) AS users
FROM activity a
LEFT JOIN occasion AS o ON a.id = o.activity_id
LEFT JOIN activity_user AS au ON a.id = au.activity_id
WHERE a.user_id = 4
GROUP BY a.id
ORDER BY a.created_at
DESC LIMIT 50
在这里,我得到了很多“场合”,但“用户”似乎是“场合”计数的副本,这是错误的。
所以我的问题是,如何修复此查询以使两个COUNT
一起工作?
COUNT()
计算非NULL值。修复查询的简单方法是使用COUNT(DISTINCT)
:
SELECT a.title, a.image,
COUNT(DISTINCT o.id) AS occasions, COUNT(DISTINCT au.id) AS users
. . .
这可能会奏效。但是,它创建了一个中间表,它是两个表(每个标题)的笛卡尔积。这可能会变得非常大。更具伸缩性的解决方案是在加入之前使用子查询和聚合。
活动用户使用的左连接限制了您的结果,因为数据库无法找到相关数据。但是当你使用LEFT OUTER JOIN时,它应该返回所有预期的行和它们的计数。