You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为SQL中连续相同letter的分段分配唯一section_number

为连续相同字母的分段分配唯一section_number的SQL解决方案

原始数据表

"letter"    "time"
"a" "2024-08-14 16:57:56.563112"
"b" "2024-08-14 17:57:56.563112"
"b" "2024-08-14 18:57:56.563112"
"b" "2024-08-14 19:57:56.563112"
"a" "2024-08-14 20:57:56.563112"
"a" "2024-08-14 21:57:56.563112"
"b" "2024-08-14 22:57:56.563112"
"b" "2024-08-14 23:57:56.563112"

需求说明

需要基于连续相同的letter为每一段分配唯一的section_number,期望结果如下:

"letter"    "time"  "section_number"
"a" "2024-08-14 16:57:56.563112"    0
"b" "2024-08-14 17:57:56.563112"    1
"b" "2024-08-14 18:57:56.563112"    1
"b" "2024-08-14 19:57:56.563112"    1
"a" "2024-08-14 20:57:56.563112"    2
"a" "2024-08-14 21:57:56.563112"    2
"b" "2024-08-14 22:57:56.563112"    3
"b" "2024-08-14 23:57:56.563112"    3

尝试的SQL及问题

之前尝试的SQL语句:

SELECT 
    letter
    ,time
    ,ROW_NUMBER() OVER(ORDER BY  time)
    - ROW_NUMBER() OVER(Partition by letter ORDER BY  time) as section_number
FROM test;

该语句生成的section_number存在重复(如编号3出现多次),实际结果如下:

"letter"    "time"  "section_number"
"a" "2024-08-14 16:57:56.563112"    0
"b" "2024-08-14 17:57:56.563112"    1
"b" "2024-08-14 18:57:56.563112"    1
"b" "2024-08-14 19:57:56.563112"    1
"a" "2024-08-14 20:57:56.563112"    3
"a" "2024-08-14 21:57:56.563112"    3
"b" "2024-08-14 22:57:56.563112"    3
"b" "2024-08-14 23:57:56.563112"    3

正确的SQL实现方案

核心思路是通过LAG()函数判断当前行与前一行的letter是否相同,标记新分段的起始点,再通过累加标记值生成唯一的分段编号:

WITH section_markers AS (
    SELECT 
        letter,
        time,
        -- 当前行与前一行letter不同时,标记为新分段的起始
        CASE 
            WHEN LAG(letter) OVER(ORDER BY time) != letter THEN 1 
            ELSE 0 
        END AS new_section_flag
    FROM test
)
SELECT 
    letter,
    time,
    -- 累加标记值,生成从0开始的连续分段编号
    SUM(COALESCE(new_section_flag, 0)) OVER(ORDER BY time) AS section_number
FROM section_markers;

逻辑说明

  1. LAG(letter) OVER(ORDER BY time):获取当前行按时间排序后的前一行letter值。
  2. new_section_flag:当当前行letter与前一行不同时,标记为1(新分段开始),否则为0。
  3. SUM(COALESCE(new_section_flag, 0)) OVER(ORDER BY time):累加标记值,第一行无前置行,用COALESCE将NULL转为0,最终得到连续唯一的分段编号。

内容的提问来源于stack exchange,提问作者Sergei Suleimanov

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.19 10:35:55