需求
id 是上表temp_id_list_0209的主键, 表每一行包含日志表中的一个 ID,现将一些 ID 从 Logs 表中删除。编写一个 SQL 查询得到 Logs 表中的连续区间的开始数字和结束数字,将查询表按照 start_id 排序。
要求输出结果为
|
start_id
|
end_id
|
|
1
|
2
|
|
4
|
6
|
|
9
|
12
|
数据准备
create table temp_id_list_0209
(
id int
) row format delimited
fields terminated by '\t'
stored as orc
tblproperties ("orc.compress" = "snappy");
insert into temp_id_list_0209
values (1),
(2),
(4),
(5),
(6),
(9),
(10),
(11),
(12)
;
select * from temp_id_list_0209;
需求实现
第一步 :获取ID,借助函数构建差值
select id,
lag(id, 1, id) over (order by id) df1,
id - lag(id, 1, id) over (order by id) df2
from temp_id_list_0209;
|
id
|
df1
|
df2
|
|
1
|
1
|
0
|
|
2
|
1
|
1
|
|
4
|
2
|
2
|
|
5
|
4
|
1
|
|
6
|
5
|
1
|
|
9
|
6
|
3
|
|
10
|
9
|
1
|
|
11
|
10
|
1
|
|
12
|
11
|
1
|
第二步、根据第一步结果,创造分组条件
select id,
sum(case when dif2 > 1 then 1 else 0 end) over (order by id) flag
from (select id, id - lag(id, 1, id) over (order by id) dif2
from temp_id_list_0209) o;
|
id
|
flag
|
|
1
|
0
|
|
2
|
0
|
|
4
|
1
|
|
5
|
1
|
|
6
|
1
|
|
9
|
2
|
|
10
|
2
|
|
11
|
2
|
|
12
|
2
|
第三步、根据flag 分组
select min(id) start_id,max(id) end_id
from (select id, sum(if(diff > 1, 1, 0)) over (order by id) as flag
from (select id
, id - lag(id, 1, id) over (order by id) as diff
from temp_id_list_0209) o) t
group by flag
order by 1;
|
start_id
|
end_id
|
|
1
|
2
|
|
4
|
6
|
|
9
|
12
|