根据PostgreSQL中的条件在组中选择一行
我有一张这样的表格(根据PostgreSQL中的条件在组中选择一行,sql,postgresql,group-by,Sql,Postgresql,Group By,我有一张这样的表格(tbl): 我想从每个组中选择一行,特别是每个组的最大值val 我可以轻松地选择grp和val: SELECT grp, MAX(val) FROM tbl GROUP BY grp 生成此表(tbl2): 但是,我想要这个表: +----+-----+------+-----+ | pk | grp | attr | val | +----+-----+------+-----+ | 1 | 0 | foha | 56 | | 3 | 1 | faso |
tbl
):
我想从每个组中选择一行,特别是每个组的最大值val
我可以轻松地选择grp
和val
:
SELECT grp, MAX(val)
FROM tbl
GROUP BY grp
生成此表(tbl2
):
但是,我想要这个表:
+----+-----+------+-----+
| pk | grp | attr | val |
+----+-----+------+-----+
| 1 | 0 | foha | 56 |
| 3 | 1 | faso | 11 |
| 5 | 2 | bnda | 12 |
+----+-----+------+-----+
由于(grp,val)
构成了一个键,我可以在grp
和val
的相同tbl2
上加入tbl
然而,我想知道是否还有其他解决方案:在我的现实世界中,tbl
是一个非常复杂和繁重的派生表,我的设计限制是不能使用临时表。是否有办法根据val
对每个组内的行进行排序,然后为每个组获取第一条记录
我使用的是PostgreSQL 10,但标准SQL解决方案是最好的。在Postgres中,最好的方法是
在上进行区分:
SELECT DISTINCT ON (t.grp) t.*
FROM tbl
ORDER BY grp, val DESC;
特别是,这可以利用(grp,val desc)
上的索引。在Postgres中,最好的方法是在上进行区分:
SELECT DISTINCT ON (t.grp) t.*
FROM tbl
ORDER BY grp, val DESC;
特别是,这可以利用(grp,val desc)
上的索引进行集成:PosgreSQL文档特别提到“SELECT DISTINCT on(表达式[,…])只保留给定表达式计算为相等的每组行的第一行。它们[…]使用与ORDER BY[…]相同的规则进行解释。请注意,每个集合的“第一行”是不可预测的,除非使用ORDER BY来确保所需的行出现在第一行。”。这将使您的在解决方案上清晰可见。需要注意的是,对于独特的
条款,在订购时没有做出相同的保证!集成:PosgreSQL文档特别提到“SELECT DISTINCT ON(表达式[,…])只保留每组行中给定表达式计算结果相等的第一行。它们[…]使用与ORDER BY[…]相同的规则进行解释。请注意,“第一行“除非使用ORDER BY来确保所需行首先出现,否则每个集合的排序都是不可预测的。”。这会使您的DISTINCT ON
解决方案正确无误。应该注意的是,对于DISTINCT
子句,在排序上不会做出相同的保证!
SELECT DISTINCT ON (t.grp) t.*
FROM tbl
ORDER BY grp, val DESC;