PostgreSQL DISTINCT 和 DISTINCT ON

select语句中,使用distinct关键字,在处理select list后,结果表能够选择消除重复的行。在SELECT以后直接写入DISTINCT关键字以指定此关键字:sql

SELECT DISTINCT select_list ...

(能够使用关键字ALL代替DISTINCT来指定保留全部行的默认行为)express

 

显然,若是两行至少有一个列值不一样,则认为它们是不一样的。在此比较中,将空值视为相等。函数

 

另外,一个任意表达式能够肯定哪些行被认为是不一样的:code

SELECT DISTINCT ON (expression [, expression ...]) select_list ...

这里的expression是一个针对全部行求值的任意值表达式。 一组全部表达式均相等的行被视为重复行,而且仅该集合的第一行保留在输出中。请注意,除非查询在足够的列上排序以保证到达DISTINCT过滤器的行的惟一顺序,不然集合的“第一行”是不可预测的。(DISTINCT ON处理在ORDER BY排序以后进行)blog

DISTINCT ON子句不是SQL标准的一部分,有时因为其结果的不肯定性而有时被认为是不良样式。经过明智地使用GROUP BYFROM中的子查询,能够避免这种构造,可是它一般是最方便的选择。排序

 

create table t_distinct(a int ,b int ,c int);
insert into t_distinct values(1,2,3);
insert into t_distinct values(2,3,4);
insert into t_distinct values(3,4,5);

insert into t_distinct values(2,2,3);
insert into t_distinct values(3,3,4);
insert into t_distinct values(4,4,5); 

insert into t_distinct(a,b) values(5,6); 
insert into t_distinct(a,b) values(5,6); 
insert into t_distinct(a,b) values(6,7); 

  

1.返回全部记录:it

# select a,b,c from t_distinct;
 a | b | c 
---+---+---
 1 | 2 | 3
 2 | 3 | 4
 3 | 4 | 5
 2 | 2 | 3
 3 | 3 | 4
 4 | 4 | 5
 5 | 6 |  
 5 | 6 |  
 6 | 7 |  
(9 rows)

# select all a,b,c from t_distinct;
 a | b | c 
---+---+---
 1 | 2 | 3
 2 | 3 | 4
 3 | 4 | 5
 2 | 2 | 3
 3 | 3 | 4
 4 | 4 | 5
 5 | 6 |  
 5 | 6 |  
 6 | 7 |  
(9 rows)

  

2.返回 a,b,c 惟一值。(这里NULL视为相等)io

# select distinct a,b,c from t_distinct;
 a | b | c 
---+---+---
 2 | 2 | 3
 5 | 6 |  
 1 | 2 | 3
 6 | 7 |  
 3 | 3 | 4
 4 | 4 | 5
 3 | 4 | 5
 2 | 3 | 4
(8 rows)

  

3.返回a惟一的任意行table

# select distinct on (a) a,b,c from t_distinct;
 a | b | c 
---+---+---
 1 | 2 | 3
 2 | 2 | 3
 3 | 3 | 4
 4 | 4 | 5
 5 | 6 |  
 6 | 7 |  
(6 rows)

使用窗口函数能够达到相似效果,可是能够肯定返回哪行,所以也更慢一些:class

# select * from (select row_number() over (partition by a) as rn, * from t_distinct) t where rn=1;  
 rn | a | b | c 
----+---+---+---
  1 | 1 | 2 | 3
  1 | 2 | 2 | 3
  1 | 3 | 3 | 4
  1 | 4 | 4 | 5
  1 | 5 | 6 |  
  1 | 6 | 7 |  
(6 rows)

  

# select distinct on (a,b) a,b,c from t_distinct;
 a | b | c 
---+---+---
 1 | 2 | 3
 2 | 2 | 3
 2 | 3 | 4
 3 | 3 | 4
 3 | 4 | 5
 4 | 4 | 5
 5 | 6 |  
 6 | 7 |  
(8 rows)


#这里NULL视为相等
# select distinct on (c) a,b,c from t_distinct;
 a | b | c 
---+---+---
 1 | 2 | 3
 3 | 3 | 4
 3 | 4 | 5
 5 | 6 |  
(4 rows)
相关文章
相关标签/搜索