SQL - 获取最大值
SQL - getting max value
下面的查询给出了计数大于 70 的结果。
SELECT books.name, COUNT(library.staff)
FROM (library INNER JOIN books
ON library.staff = books.id)
GROUP BY library.staff,books.id
HAVING COUNT(library.staff) > 70;
如何修改查询以获得 最大 计数的结果?
一种方法是order by
和limit
:
SELECT b.name, COUNT(l.staff) as cnt
FROM library l INNER JOIN
books b
ON l.staff = b.id
GROUP BY l.staff, b.name
ORDER BY cnt DESC
LIMIT 1;
您按两列分组,但 select
中只有一列,我觉得很奇怪。但是,如果查询有效,那么它只是在查找重复项。
你可以这样做
SELECT books.name, COUNT(library.staff)
FROM (library INNER JOIN books
ON library.staff = books.id)
GROUP BY library.staff,books.id
HAVING COUNT(library.staff) = (select max(library.staff) from library);
您可以使用 ORDER BY() DESC 和 LIMIT 1
SELECT books.name, COUNT(library.staff)
FROM (library INNER JOIN books
ON library.staff = books.id)
GROUP BY library.staff,books.id
ORDER BY COUNT(library.staff) DESC
LIMIT 1
真的吗?
您加入 library.staff = books.id
。这是一个令人惊讶的命名约定。一本书的ID等于图书馆的“职员”?您应该提供 table 定义和一些解释...
为了这个答案的目的,我们假设这是正确的。
审核查询
除了使用 table 别名以提高可读性之外,您还可以在几个地方进行简化:
SELECT b.id, b.name, count(*) AS ct
FROM library l
JOIN books b ON b.id = l.staff
GROUP BY b.id -- l.staff -- redundant
HAVING count(*) > 70;
因为你是在b.id = l.staff
上加入的,l.staff
肯定是NOT NULL
,所以用count(*)
比较快一点做同样的事情(count 的单独实现,它只计算行而不查看列)。
GROUP BY b.id
在这种情况下没有 l.staff
也一样。
但由于您是按 b.id
分组,而不是按 b.name
分组,因此可能存在重复名称,我们只能通过在结果中添加 id
来区分- 除非 name
是唯一的,您没有指定。
更快的查询
假设books.id
是主键这似乎是合理的:
SELECT b.id, b.name, l.ct
FROM books b
JOIN (
SELECT staff AS id, count(*) AS ct
FROM library
GROUP BY 1
) l USING (id)
HAVING count(*) > 70;
阅读整个 table 或其中的大部分内容,通常先聚合然后加入要快得多。
- Aggregate a single column in query with many columns
用 EXPLAIN ANALYZE
测试。
回答
要获得最大计数的结果,ORDER BY count(*) DESC LIMIT 1
与提供的其他答案一样通常是最快的选择 - 获得 一个 获胜者.
获得所有位获奖者:
SELECT b.id, b.name, l.ct
FROM books b
JOIN (
SELECT staff AS id, count(*) AS ct
, rank() OVER (ORDER BY count(*) DESC) AS rnk
FROM library
GROUP BY 1
) l USING (id)
WHERE l.rnk = 1;
在这里使用window function rank()
(不是row_number()
)。
请注意,您可以在单个 SELECT
:
中组合聚合函数和 window 函数
- Get the distinct sum of a joined table column
下面的查询给出了计数大于 70 的结果。
SELECT books.name, COUNT(library.staff)
FROM (library INNER JOIN books
ON library.staff = books.id)
GROUP BY library.staff,books.id
HAVING COUNT(library.staff) > 70;
如何修改查询以获得 最大 计数的结果?
一种方法是order by
和limit
:
SELECT b.name, COUNT(l.staff) as cnt
FROM library l INNER JOIN
books b
ON l.staff = b.id
GROUP BY l.staff, b.name
ORDER BY cnt DESC
LIMIT 1;
您按两列分组,但 select
中只有一列,我觉得很奇怪。但是,如果查询有效,那么它只是在查找重复项。
你可以这样做
SELECT books.name, COUNT(library.staff)
FROM (library INNER JOIN books
ON library.staff = books.id)
GROUP BY library.staff,books.id
HAVING COUNT(library.staff) = (select max(library.staff) from library);
您可以使用 ORDER BY() DESC 和 LIMIT 1
SELECT books.name, COUNT(library.staff)
FROM (library INNER JOIN books
ON library.staff = books.id)
GROUP BY library.staff,books.id
ORDER BY COUNT(library.staff) DESC
LIMIT 1
真的吗?
您加入 library.staff = books.id
。这是一个令人惊讶的命名约定。一本书的ID等于图书馆的“职员”?您应该提供 table 定义和一些解释...
为了这个答案的目的,我们假设这是正确的。
审核查询
除了使用 table 别名以提高可读性之外,您还可以在几个地方进行简化:
SELECT b.id, b.name, count(*) AS ct
FROM library l
JOIN books b ON b.id = l.staff
GROUP BY b.id -- l.staff -- redundant
HAVING count(*) > 70;
因为你是在
b.id = l.staff
上加入的,l.staff
肯定是NOT NULL
,所以用count(*)
比较快一点做同样的事情(count 的单独实现,它只计算行而不查看列)。GROUP BY b.id
在这种情况下没有l.staff
也一样。但由于您是按
b.id
分组,而不是按b.name
分组,因此可能存在重复名称,我们只能通过在结果中添加id
来区分- 除非name
是唯一的,您没有指定。
更快的查询
假设books.id
是主键这似乎是合理的:
SELECT b.id, b.name, l.ct
FROM books b
JOIN (
SELECT staff AS id, count(*) AS ct
FROM library
GROUP BY 1
) l USING (id)
HAVING count(*) > 70;
阅读整个 table 或其中的大部分内容,通常先聚合然后加入要快得多。
- Aggregate a single column in query with many columns
用 EXPLAIN ANALYZE
测试。
回答
要获得最大计数的结果,ORDER BY count(*) DESC LIMIT 1
与提供的其他答案一样通常是最快的选择 - 获得 一个 获胜者.
获得所有位获奖者:
SELECT b.id, b.name, l.ct
FROM books b
JOIN (
SELECT staff AS id, count(*) AS ct
, rank() OVER (ORDER BY count(*) DESC) AS rnk
FROM library
GROUP BY 1
) l USING (id)
WHERE l.rnk = 1;
在这里使用window function rank()
(不是row_number()
)。
请注意,您可以在单个 SELECT
:
- Get the distinct sum of a joined table column