SQL需求:为数据表添加非空日期对应的下一阶段编号列
需求说明
需要为现有数据表新增Next_Stage列,该列展示当前行之后第一个STAGE_ENTERED_DATE不为null的STAGE_NO。
输入数据表
| STAGE_NO | STAGE_ENTERED_DATE |
|---|---|
| 0 | 2015-12-01 14:16:47 |
| 1 | null |
| 2 | null |
| 3 | null |
| 4 | null |
| 5 | null |
| 6 | 2017-02-12 0:00:00 |
| 7 | 2017-12-12 0:00:00 |
期望输出结果
| STAGE_NO | STAGE_ENTERED_DATE | Next_Stage |
|---|---|---|
| 0 | 2015-12-01 14:16:47 | 6 |
| 1 | null | 6 |
| 2 | null | 6 |
| 3 | null | 6 |
| 4 | null | 6 |
| 5 | null | 6 |
| 6 | 2017-02-12 0:00:00 | 7 |
| 7 | 2017-12-12 0:00:00 | null |
解决方案
通用SQL实现(适配MySQL 8.0+、SQL Server、PostgreSQL等)
WITH staged_data AS ( SELECT STAGE_NO, STAGE_ENTERED_DATE, -- 倒序窗口填充后续最近的非空阶段编号 LAST_VALUE(CASE WHEN STAGE_ENTERED_DATE IS NOT NULL THEN STAGE_NO END) OVER (ORDER BY STAGE_NO DESC ROWS BETWEEN CURRENT ROW AND UNBOUNDED FOLLOWING) AS next_stage_candidate FROM your_table_name ) SELECT STAGE_NO, STAGE_ENTERED_DATE, -- 对自身有非空日期的行,取下一个候选值;空日期行直接用候选值 CASE WHEN STAGE_ENTERED_DATE IS NOT NULL THEN LEAD(next_stage_candidate) OVER (ORDER BY STAGE_NO) ELSE next_stage_candidate END AS Next_Stage FROM staged_data ORDER BY STAGE_NO;
简洁版(支持IGNORE NULLS的数据库:PostgreSQL、Oracle等)
如果数据库支持窗口函数的IGNORE NULLS参数,可以直接用更简洁的写法:
SELECT STAGE_NO, STAGE_ENTERED_DATE, LEAD(CASE WHEN STAGE_ENTERED_DATE IS NOT NULL THEN STAGE_NO END IGNORE NULLS) OVER (ORDER BY STAGE_NO) AS Next_Stage FROM your_table_name;
注:
IGNORE NULLS会让LEAD自动跳过null值,直接定位到下一个非空的阶段编号。
内容的提问来源于stack exchange,提问作者Shru
相关产品推荐
相关产品推荐

