如何使用聚合函数连接相关查询的数据?

时间:2016-02-18 11:40:00

标签: mysql sql

我有下表:

userActions:
id | uId | goodAction | actionOverridden | dateAdded

我写了一个查询来获取:

  • 良好操作的数量(goodAction = 1)行
  • 错误操作的数量(goodAction = 0
  • 的行数
  • 被覆盖的操作数(actionOverridden = 1
  • 的行数


SELECT

(SELECT COUNT(*)
FROM userActions ua
WHERE ua.goodAction = 0 AND ua.dateAdded > NOW() - INTERVAL 1 year AND ua.uId = 520) badActions,

(SELECT COUNT(*)
FROM userActions ua
WHERE ua.goodAction = 1 AND ua.dateAdded > NOW() - INTERVAL 1 year AND ua.uId = 520) goodActions,

(SELECT COUNT(*)
FROM userActions ua
WHERE ua.actionOverridden = 1 AND ua.dateAdded > NOW() - INTERVAL 1 year AND ua.uId = 520) actionOverrides

以上查询获取ID为520的用户的数据,但我想为所有用户获取此信息。通过上面的查询,我需要获取PHP中的用户列表,然后循环遍历列表并执行上述查询,注入用户ID。

如何修改上述查询以使其检索所有用户的数据?

我知道需要从子查询中删除AND ua.uId = 520条件,我认为GROUP BY ua.uId将在子查询之外使用,但我不确定该做什么。

2 个答案:

答案 0 :(得分:5)

您可以使用CASE表达式而不是所有这些相关查询,并使用group by来获取所有用户的结果,如下所示:

SELECT t.uID,
       sum(case when t.goodAction = 0 then 1 else 0 end) as badActions,
       sum(case when t.goodAction = 1 then 1 else 0 end) as goodActions,
       sum(case when t.actionOverridden = 1 then 1 else 0 end) as actionOverrides
FROM userActions t
WHERE t.dateAdded > NOW() - INTERVAL 1 year
GROUP BY t.uID

答案 1 :(得分:2)

您可以将COUNT和NULLIF组合并按uID组合:

SELECT t.uID,
       COUNT(NULLIF(1, t.goodAction)) AS badActions,
       COUNT(NULLIF(0, t.goodAction)) AS goodActions,
       COUNT(NULLIF(0, t.actionOverridden)) AS actionOverrides
FROM userActions t
WHERE t.dateAdded > NOW() - INTERVAL 1 year
GROUP BY t.uID;