sql - 获取总数和前 3 列
问题描述
我有以下 SQL 查询:
SELECT TOP 3 accounts.username
,COUNT(accounts.username) AS count
FROM relationships
JOIN accounts ON relationships.account = accounts.id
WHERE relationships.following = 4
AND relationships.account IN (
SELECT relationships.following
FROM relationships
WHERE relationships.account = 8
);
我想返回accounts.username 和前3 个accounts.username 的总数(没有特别的顺序)。可惜不能共存accounts.username
。COUNT(accounts.username)
该查询可以很好地删除其中一个。我不想使用不同的选择主体两次发送请求。计数列可以跨越到 1000+,所以我更喜欢在 SQL 中而不是在代码中计算它。
当前查询返回的错误Column 'accounts.username' is invalid in the select list because it is not contained in either an aggregate function or the GROUP BY clause.
没有带我到任何地方,这与其他问题不同,因为我不想使用“分组依据”子句。有没有办法做到这一点FOR JSON AUTO
?
所需的输出可能是:
+-------+----------+
| count | username |
+-------+----------+
| 1551 | simon1 |
| 1551 | simon2 |
| 1551 | simon3 |
+-------+----------+
或者
+----------------------------------------------------------------+
| JSON_F52E2B61-18A1-11d1-B105-00805F49916B |
+----------------------------------------------------------------+
| [{"count": 1551, "usernames": ["simon1", "simon2", "simon3"]}] |
+----------------------------------------------------------------+
解决方案
如果要username
在结果集中的附加列中显示满足过滤条件(并且其中不为空)的总行数,则可以使用窗口函数:
SELECT TOP 3
a.username,
COUNT(a.username) OVER() AS cnt
FROM relationships r
JOIN accounts a ON r.account = a.id
WHERE
r.following = 4
AND EXISTS (
SELECT 1 FROM relationships t1 WHERE r1.account = 8 AND r1.following = r.account
)
;
旁注:
- 如果
username
不可为空,则使用COUNT(*)
而不是COUNT(a.username)
:这更有效,因为它不需要数据库检查每个值是否为空 - 表别名使查询更易于编写、读取和维护
- 我通常更喜欢
EXISTS
(IN
但这主要是一个口味问题,因为这两种技术都应该适合您的用例)
推荐阅读
- java - 如何在android中以编程方式在片段之间导航?
- php - 如何在 url 中定义没有 '?{name}=' 的 post 变量?
- python - 为什么即使使用双端队列而不是列表,我仍然会收到“由于超时错误而终止”?
- go - 加载具有关联的模型
- c++ - STM32L4 Rx中断:没有调试错误就无法工作
- java - 在控制器中抛出 ResponseStatusException 不返回正文
- mysql - 如何模拟链接服务器宕机?
- asp.net-core - 是否可以使用不同的发件人电子邮件和配置电子邮件从 ASP.Net Core 中的 MimeKit 发送电子邮件?
- javascript - 如何使用 JavaScript 制作一个给出 3 位数加法问题和个位数乘法问题的数学问题生成器?
- python - 列表的聚合列