带有排序依据的 SQL 分组依据

Posted

技术标签:

【中文标题】带有排序依据的 SQL 分组依据【英文标题】:SQL Group By with an Order By 【发布时间】:2010-09-06 21:05:21 【问题描述】:

我有一个标签表,想从列表中获取最高计数的标签。

示例数据如下所示

id (1) tag ('night')
id (2) tag ('awesome')
id (3) tag ('night')

使用

SELECT COUNT(*), `Tag` from `images-tags`
GROUP BY `Tag`

让我找回我正在寻找的完美数据。不过,我想整理一下,让最高标签数排在第一位,并限制它只向我发送前 20 个左右。

我试过了……

SELECT COUNT(id), `Tag` from `images-tags`
GROUP BY `Tag`
ORDER BY COUNT(id) DESC
LIMIT 20

我不断收到“无效使用组功能 - ErrNr 1111”

我做错了什么?

我正在使用 mysql 4.1.25-Debian

【问题讨论】:

【参考方案1】:

在所有版本的 MySQL 中,只需对 SELECT 列表中的聚合进行别名,并按别名排序:

SELECT COUNT(id) AS theCount, `Tag` from `images-tags`
GROUP BY `Tag`
ORDER BY theCount DESC
LIMIT 20

【讨论】:

恕我直言,这是比所选答案更干净的版本。立即清楚订购的是什么。当然,如果它是一个快速脚本,那并不重要。 虽然 OP 使用的是 MySQL,但这个答案在 HSQL(Libreoffice 内置)中也适用于我【参考方案2】:

MySQL 5 之前的版本不允许在 ORDER BY 子句中使用聚合函数。

您可以使用已弃用的语法绕过此限制:

SELECT COUNT(id), `Tag` from `images-tags`
GROUP BY `Tag`
ORDER BY 1 DESC
LIMIT 20

1,因为它是您要分组的第一列。

【讨论】:

【参考方案3】:

我不了解 MySQL,但是在 MS SQL 中,您可以在 order by 子句中使用列索引。我之前在使用 group bys 进行计数时已经这样做了,因为它往往更容易使用。

所以

SELECT COUNT(id), `Tag` from `images-tags`
GROUP BY `Tag`
ORDER BY COUNT(id) DESC
LIMIT 20

变成

SELECT COUNT(id), `Tag` from `images-tags`
GROUP BY `Tag`
ORDER 1 DESC
LIMIT 20

【讨论】:

【参考方案4】:

在 Oracle 中,这样的事情可以很好地将计数和排序分开一点。我不确定它是否适用于 MySql 4。

select 'Tag', counts.cnt
from
  (
  select count(*) as cnt, 'Tag'
  from 'images-tags'
  group by 'tag'
  ) counts
order by counts.cnt desc

【讨论】:

似乎在 10.1.14-MariaDB(与 MySQL 兼容)中对我有用。我以为我必须拥有) as counts,但没有as 部分它仍然有效。【参考方案5】:

试试这个查询

 SELECT  data_collector_id , count (data_collector_id ) as frequency 
    from rent_flats 
    where is_contact_person_landlord = 'True' 
    GROUP BY data_collector_id 
    ORDER BY count(data_collector_id) DESC

【讨论】:

这与问题有什么关系?字段甚至不一样。

以上是关于带有排序依据的 SQL 分组依据的主要内容,如果未能解决你的问题,请参考以下文章

新列的 SQL 不同分组依据

分组依据/排序依据的 MySQL 索引

这两种 MySQL 查询形式总是等价的吗?分组依据 + 排序依据 + 限制

分组依据、IFNULL 和按日期排序

Laravel Eloquent 查询,带有连接、计数和分组依据

SQL 中 XML 路径的分组依据