SQL按id分组校验事件日期顺序并生成event_check字段的实现问题
事件序列校验需求实现
你现有一张数据表t_event,包含3个字段:
id:分组标识event_name:事件名称,取值包含a、b、c三类event_date:事件发生日期,为可比较的日期/时间戳类型
校验逻辑说明
按id分组后执行以下逻辑:
- 首先判断分组内是否存在
event_name = 'b'的记录:- 不存在:新增字段
event_check赋值为missing b - 存在:继续校验三类事件的日期顺序:
- 满足
a对应的event_date < b对应的event_date < c对应的event_date→ 返回ok - 满足
b对应的event_date < a对应的event_date→ 返回too early - 满足
c对应的event_date < b对应的event_date→ 返回too late
- 满足
- 不存在:新增字段
通用SQL实现
WITH event_pivot AS ( SELECT id, MAX(CASE WHEN event_name = 'a' THEN event_date END) AS a_date, MAX(CASE WHEN event_name = 'b' THEN event_date END) AS b_date, MAX(CASE WHEN event_name = 'c' THEN event_date END) AS c_date FROM t_event GROUP BY id ) SELECT id, CASE WHEN b_date IS NULL THEN 'missing b' WHEN a_date < b_date AND b_date < c_date THEN 'ok' WHEN b_date < a_date THEN 'too early' WHEN c_date < b_date THEN 'too late' ELSE 'unknown' -- 可根据实际业务补充边界场景返回值 END AS event_check FROM event_pivot;
实现说明
- 先用CTE做行转列,把同一个id下三类事件的日期聚合到同一行,简化后续比较逻辑
- 若同一个id下存在多个同名事件,当前用
MAX取最新的事件日期,如需取最早的可直接替换为MIN - 校验逻辑按业务优先级排序,不会出现判断冲突
- 兼容所有支持CASE WHEN和GROUP BY的SQL引擎,包括MySQL 5.7+、PostgreSQL、Hive、Spark SQL等
内容的提问来源于stack exchange,提问作者Romero Azzalini
相关产品推荐
相关产品推荐

