繁体   English   中英

postgres查询以基于某些列的多个副本获取第一行

[英]postgres query to get first row based on multiple copies of some columns

假设我有一张桌子-

A        B       C  
1        3       5  
1        3       7  
1        3       9  
2        4       3  
2        4       6  
2        4       1 

在这里,A和B的相同组合有多个副本。对于每个组合,我想返回它的第一个条目。 所以我想成为这张桌子的结果是

A        B      C  
1        3      5  
2        4      3 

如何在Postgres SQL中执行此操作?

假设你可以在A,B一类的术语定义“第一”,和你ç想DISTINCT ON这一点。

SELECT
  DISTINCT ON ("A", "B")
  "A", "B", "C"
FROM Table1
ORDER BY "A", "B", "C";

例如http://sqlfiddle.com/#!15/9ca16/1

有关DISTINCT ON更多信息,请参见SELECT


如果您犯了一个严重的错误,即假定SQL表具有固有的顺序,那么您将需要在继续操作之前先对表进行修复。 您可以使用PostgreSQL ctid伪列来指导创建与当前磁盘表顺序匹配的主键。 仅仅应该安全:

ALTER TABLE mytable ADD COLUMN id SERIAL PRIMARY KEY;

因为PostgreSQL倾向于按表顺序编写密钥。 没有保证,但是没有主键时也没有其他保证。 那么你也能:

SELECT
  DISTINCT ON ("A", "B")
  "A", "B", "C"
FROM Table1
ORDER BY id;

(编辑:我不建议在应用程序中查询时使用ctid 。这是解决特定问题的便捷工具,但它不是PostgreSQL中的真正公共API,也不是SQL标准的一部分。这与Oracle中的ROWID ,它会由于真空等原因而发生更改。PostgreSQL可以随意在将来的版本中对其进行破坏/更改/删除。)

那么,你可以排序的做到这一点。 SQL表没有顺序的概念,因此您确实需要一列来指定顺序。 以下代码从每个组返回任意行:

select distinct on(a, b) a, b, c
from table t
order by a, b;

通常,您将使用类似:

select distinct on(a, b) a, b, c
from table t
order by a, b, id desc;

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM