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

如何在T-SQL中创建遇NULL值重置的累计求和列

需求:创建遇NULL重置的分区累计求和列

需要为数据集生成Running_T累计求和列,满足以下规则:

  • 按ID字段分区,每个ID单独计算累计
  • 按date字段保持顺序排序
  • 每次遇到单个或连续多个NULL值时,累计求和结果重置;且NULL对应的Running_T值也为NULL

期望结果如下:

IDdatevalueRunning_T
SA22310/07/201833
SA22311/07/201869
SA22325/07/2018NULLNULL
SA22316/08/20181111
SA22317/08/2018920
SA55515/05/201944
SA55527/05/20191317
SA55511/07/2019NULLNULL
SA55521/11/2019NULLNULL
SA55520/02/202044
SA55527/05/202015
SA55523/07/202027

尝试了以下代码,但无法正确处理NULL重置,还打乱了排序:

SELECT ID
       , date
       , value
       ,Running_T = SUM(value) OVER(PARTITION BY ID, (CASE WHEN [value] IS NOT NULL THEN [value] ELSE NULL END) ORDER BY [date])
FROM dim.event_data

解决方案

正确的思路是先为每个连续的非NULL区间创建分组标识,再基于分组计算累计求和:

WITH grouped_data AS (
    SELECT 
        ID,
        date,
        value,
        -- 生成分组标识:每个ID下,遇到NULL则分组编号递增,连续非NULL属于同一组
        group_id = SUM(CASE WHEN value IS NULL THEN 1 ELSE 0 END) OVER (PARTITION BY ID ORDER BY date ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW)
    FROM dim.event_data
)
SELECT 
    ID,
    date,
    value,
    Running_T = CASE 
        WHEN value IS NULL THEN NULL 
        ELSE SUM(value) OVER (PARTITION BY ID, group_id ORDER BY date) 
    END
FROM grouped_data
ORDER BY ID, date;

逻辑说明:

  1. 分组标识生成:通过SUM(CASE WHEN value IS NULL THEN 1 ELSE 0 END)窗口函数,按ID分区、日期排序,累计到当前行的NULL数量。每遇到一个NULL,分组编号就加1,这样连续的非NULL行就会拥有相同的group_id,NULL行则会开启新的分组(但后续计算时会跳过这些行的累计)。
  2. 累计求和计算:基于ID和group_id分区,按日期排序计算累计求和;同时通过CASE语句,将value为NULL的行的Running_T设为NULL,符合需求。

原代码问题分析:

原代码的PARTITION BY使用了value本身,这会把相同value的行分到同一组,完全不符合"连续非NULL区间"的分组逻辑,导致累计求和混乱,也无法正确处理NULL的重置需求。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.18 18:53:18