SQL实现按顺序分组并为子项填充对应父项Name_key
SQL分组需求:为Adult及后续Child添加父级Name_key
原始表
从test表获取的初始数据:
| Position | Name | Name_key |
|---|---|---|
| 1 | Adult | 123 |
| 2 | Child | 555 |
| 3 | Child | 666 |
| 4 | Adult | 456 |
| 5 | Child | 777 |
| 6 | Adult | 789 |
| 7 | Child | 888 |
| 8 | Child | 999 |
需求说明
按表中Position的顺序,将每个Adult与其后续的Child划分为同一组,新增parent_name_key列,使分组内所有行共享对应Adult的Name_key,最终结果如下:
| Position | Name | Name_key | parent_name_key |
|---|---|---|---|
| 1 | Adult | 123 | 123 |
| 2 | Child | 555 | 123 |
| 3 | Child | 666 | 123 |
| 4 | Adult | 456 | 456 |
| 5 | Child | 777 | 456 |
| 6 | Adult | 789 | 789 |
| 7 | Child | 888 | 789 |
| 8 | Child | 999 | 789 |
解决方案
方法一:分组标识+MAX窗口函数
先通过累计求和生成分组ID,再基于分组提取对应Adult的Name_key:
SELECT position, name, name_key, MAX(CASE WHEN name = 'Adult' THEN name_key END) OVER (PARTITION BY group_id ORDER BY position) AS parent_name_key FROM ( SELECT position, name, name_key, -- 每遇到Adult就给分组ID加1,实现Adult与后续Child同组 SUM(CASE WHEN name = 'Adult' THEN 1 ELSE 0 END) OVER (ORDER BY position) AS group_id FROM test ) t ORDER BY position;
方法二:LAST_VALUE窗口函数(更简洁)
直接取当前行及之前最后出现的Adult的Name_key:
SELECT position, name, name_key, LAST_VALUE(CASE WHEN name = 'Adult' THEN name_key END) OVER ( ORDER BY position -- 窗口范围限定为从第一行到当前行,确保只取之前的Adult ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW ) AS parent_name_key FROM test ORDER BY position;
说明
- 两种方法都依赖
Position列的顺序,确保数据按预期分组。 - 方法二更直接,无需子查询,适合新手理解和使用。
内容的提问来源于stack exchange,提问作者paymentkickball
相关产品推荐
相关产品推荐

