首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >SQL identify行之间的状态转换

SQL identify行之间的状态转换
EN

Stack Overflow用户
提问于 2020-11-15 03:42:11
回答 1查看 38关注 0票数 1

我有一个事实表,它以类似于下面的格式存储单个级别的历史状态:

代码语言:javascript
复制
---------------------------
| person |  year | state |
---------------------------
| P1     | 2001  | S1    |
| P1     | 2002  | S1    | 
| P1     | 2003  | S2    | 
...
| PN     | ...   | SX    |
--------------------------

我正在尝试计算每个人的连续年份之间的“过渡”,预期产出将是

代码语言:javascript
复制
-------------------------------------
| person |  year | state | year | state |
-------------------------------------
| P1     | 2001  | S1    | 2002 | S1
| P1     | 2002  | S1    | 2003 | S2
| P1     | 2003  | S2    | 2004 | ..
...
| PN     | ...   | SX    | ...  | ..
-------------------------------------

我本打算像下面这样自己连接这个表,但是,这个表很大,这感觉像是一个完整的笛卡尔连接。我想知道是否有更有效的方法,如窗口函数或类似的,可以更有效和优雅。

代码语言:javascript
复制
select 
    t1.person, 
    t1.year, 
    t1.state, 
    t2.year as year_next, 
    t2.state as state_next
from table t1
inner join table t2 
on t1.person = t2.person 
and t1.year + 1 = t2.year;

有什么想法?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2020-11-15 04:21:09

您可以使用LEAD()窗口函数来完成此操作。

如果年份之间没有间隔:

代码语言:javascript
复制
select *, 
  lead(year) over (partition by person order by year) next_year,
  lead(state) over (partition by person order by year) next_state
from tablename
order by person, year

如果年份之间有差距:

代码语言:javascript
复制
select person, year, state,
       case when next_year = year + 1 then next_year end next_year,
       case when next_year = year + 1 then next_state end next_state
from (
  select *, 
    lead(year) over (partition by person order by year) next_year,
    lead(state) over (partition by person order by year) next_state
  from tablename
) t
order by person, year
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/64837925

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档