首页 > 解决方案 > 根据 MySQL 中的多列获取最大的行

问题描述

我有一个看起来像的表:

id | title | value | language
---+-------+-------+---------
1  | a     | 1800  |    NULL
2  | a     | 1900  |    NULL
3  | b     | 1700  |    NULL
4  | b     | 1750  |    NULL 
5  | b     | 1790  |    1
6  | c     | 1892  |    NULL
7  | c     | 1900  |    1
8  | c     | 1910  |    2
9  | d     | 3020  |    NULL

想要得到以下结果:

id | title | value | language
---+-------+-------+---------
2  | a     | 1900  |    NULL
4  | b     | 1750  |    NULL 
5  | b     | 1790  |    1
6  | c     | 1892  |    NULL
7  | c     | 1900  |    1
8  | c     | 1910  |    2
9  | d     | 3020  |    NULL

关键是在每个标题的每种语言的值列中选择最大值 - 最大的是最新的。其次,想避免像 MAX、DISTINCT 或 GROUP-BY 这样的聚合函数,因为我正在使用 MERGE 算法构建 MySQL 视图,并且不想最终创建一个临时表(参见https://的底部dev.mysql.com/doc/refman/5.6/en/view-algorithms.html)。

到目前为止,这可行,但仅返回每个标题的最大行:

SELECT t1.title
FROM table t1
LEFT OUTER JOIN table t2
  ON t1.title = t2.title
        AND t1.value < t2.value
WHERE t2.title IS NULL

我怎样才能创建一个像上面的结果一样考虑语言的?谢谢。

标签: mysqlgreatest-n-per-groupmysql-5.7

解决方案


你可以这样做NOT EXISTS

select t.*
from tablename t
where not exists (
  select 1 from tablename
  where 
    title = t.title and 
    coalesce(language, 0) = coalesce(t.language, 0) and 
    value > t.value
)

请参阅演示
结果:

| id  | title | value | language |
| --- | ----- | ----- | -------- |
| 2   | a     | 1900  | NULL     |
| 4   | b     | 1750  | NULL     |
| 5   | b     | 1790  | 1        |
| 6   | c     | 1892  | NULL     |
| 7   | c     | 1900  | 1        |
| 8   | c     | 1910  | 2        |
| 9   | d     | 3020  | NULL     |

推荐阅读