2016-12-27 19 views
1

我有两列如下:如何在PostgreSQL中查找两个整数系列之间的重叠?

start end  id 
120  125 1 
1  13  2 
14  17  3 
100  121 4 
99  100 5 
2   6  6 

正如你可以看到有id=4 and id=5id=1 and id=4id=6 and id=2

之间的重叠我要​​指出,start始终小于或等于end

如何使用SQL查找这些重叠? 基本上我想要得到的结果是:

1 
2 
4 
5 
6 

回答

1

你会得到与其他使用exists重叠任何ID:我认为这将是看IDS的更加有用

select id 
from t 
where exists (select 1 
       from t t2 
       where t2.start <= t.end and t2.end >= t.start and t2.id <> t.id 
      ); 

重叠的:

select t.id, t2.id 
from t t join 
    t t2 
    on t2.start <= t.end and t2.end >= t.start and t.id < t2.id; 

编辑:

这里是它的工作演示:

with t (start, "end", id) as (
    values (120, 125, 1), 
      (1, 13, 2), 
      (14, 17, 3), 
      (100, 121, 4), 
      (99, 100, 5), 
      (2, 6, 6) 
    ) 
select id 
from t 
where exists (select 1 
       from t t2 
       where t2.start <= t."end" and t2."end" >= t.start and t.id <> t2.id 
      ); 
+0

它有一个重大缺陷......它只是从ID更高的IDS检查....这意味着如果我添加where条件的特定ID例如t.id = 4 ...它不会将它与id = 2进行比较。 – avi

+0

“存在”解决方案是不正确的,它也给出了'id = 3',它不与任何其他系列重叠。 – MtwStark

0
select distinct d1.id 
    --, d2.id id_overlap -- if you want to see the overlapping serie id uncomment this line 
from t d1 
join t d2 on 
    (d1.id <> d2.id) and 
    ( 
    (d1.start between d2.start and d2.[end] or d1.[end] between d2.start and d2.[end]) 
    or 
    (d2.start between d1.start and d1.[end] or d2.[end] between d1.start and d1.[end]) 
    ) 
相关问题