如何在SQL中实现跨12个月的条件标记与滞后检查
按ID跟踪过去12个月内X≠C的标记方案
嘿,我来帮你搞定这个需求!你需要给每条记录生成一个Flag,标记同ID下该记录过去12个月范围内是否存在X不等于'C'的情况,Flag=1表示存在,0表示不存在对吧?
先看一下你的原始数据表:
| DataDt | ID | X | Y |
|---|---|---|---|
| 1.1.10 | 1 | C | 7 |
| 2.1.10 | 1 | C | 5 |
| 3.1.10 | 1 | C | 4 |
| 4.1.10 | 1 | C | 8 |
| 5.1.10 | 1 | C | 1 |
| 6.1.10 | 1 | 3 | 2 |
| 7.1.10 | 1 | 6 | 7 |
| 8.1.10 | 1 | C | 7 |
| 1.1.10 | 2 | C | 7 |
| 2.1.10 | 2 | C | 7 |
| 3.1.10 | 2 | 3 | 7 |
| 4.1.10 | 2 | C | 7 |
解决方案(SQL实现)
我们可以用窗口函数来实现这个逻辑,核心是给每个ID划分时间窗口(过去12个月到当前记录),然后在窗口内判断是否有X≠'C'的记录。以下是通用的SQL代码(不同数据库可能需要微调日期区间写法,比如MySQL用INTERVAL 12 MONTH,PostgreSQL用INTERVAL '12 months'):
SELECT DataDt, ID, X, Y, -- 在过去12个月的窗口内,判断是否存在X≠'C'的记录,存在则Flag=1,否则0 MAX(CASE WHEN X != 'C' THEN 1 ELSE 0 END) OVER ( PARTITION BY ID ORDER BY DataDt RANGE BETWEEN INTERVAL '12 months' PRECEDING AND CURRENT ROW ) AS Flag FROM your_table_name;
代码解释
PARTITION BY ID:按ID分组,确保我们只在同一个ID的范围内计算标记ORDER BY DataDt:按日期排序,保证时间窗口的顺序逻辑正确RANGE BETWEEN INTERVAL '12 months' PRECEDING AND CURRENT ROW:定义当前记录往前推12个月的时间范围作为计算窗口MAX(CASE WHEN X != 'C' THEN 1 ELSE 0 END):在窗口内只要有一条X≠'C'的记录,MAX就会返回1,否则返回0,正好对应我们需要的Flag值
完整期望输出结果
按照这个逻辑,最终的输出表格会是这样:
| DataDt | ID | X | Y | Flag |
|---|---|---|---|---|
| 1.1.10 | 1 | C | 7 | 0 |
| 2.1.10 | 1 | C | 5 | 0 |
| 3.1.10 | 1 | C | 4 | 0 |
| 4.1.10 | 1 | C | 8 | 0 |
| 5.1.10 | 1 | C | 1 | 0 |
| 6.1.10 | 1 | 3 | 2 | 1 |
| 7.1.10 | 1 | 6 | 7 | 1 |
| 8.1.10 | 1 | C | 7 | 1 |
| 1.1.10 | 2 | C | 7 | 0 |
| 2.1.10 | 2 | C | 7 | 0 |
| 3.1.10 | 2 | 3 | 7 | 1 |
| 4.1.10 | 2 | C | 7 | 1 |
内容的提问来源于stack exchange,提问作者I.m.rich
相关产品推荐
相关产品推荐

