SQL Server 在MSSQL中使用LAG根据前一列条目从当前条目中减去值将返回NULL

nx7onnlm  于 2023-01-08  发布在  其他
关注(0)|答案(2)|浏览(125)

我试图解析一个表中的closing_stock_quantity列,该表中有0个值,实际上应该是前一个closing_stock_quantity和当前日期的quantity_sold的差值(其中0值为)。也就是说,从前一个quantity_closing_stock条目中减去当天的销售量,以获得当天的quantity_closing_stock。
注:没有获取quantity_closing_stock的逻辑,它只是已检索的数据。
到目前为止,我已经尝试过检索NULL值来代替我试图计算的这些条目。
以下是初始示例数据:
| 单元_id|时间戳|数量|数量_期末_库存|
| - ------| - ------| - ------| - ------|
| 1个|2022年1月1日|无|一百|
| 1个|2022年1月2日|1个|九十九|
| 1个|2022年1月3日|三个|九十六|
| 1个|2022年1月4日|六个|九十|
| 1个|2022年1月5日|1个|无|
| 1个|2022年1月6日|第二章|一百|
| 1个|2022年1月7日|五个|九十五|
我已经尝试使用LAG函数来解决这个问题,但是我收到了这些条目的NULL值。
预期输出应为:
| 单元_id|时间戳|数量|数量_期末_库存|
| - ------| - ------| - ------| - ------|
| 1个|2022年1月1日|无|一百|
| 1个|2022年1月2日|1个|九十九|
| 1个|2022年1月3日|三个|九十六|
| 1个|2022年1月4日|六个|九十|
| 1个|2022年1月5日|1个|八十九|
| 1个|2022年1月6日|第二章|一百|
| 1个|2022年1月7日|五个|九十五|
下面是我尝试过的代码:

WITH mycte ([timestamp],quantity_closing_stock)  AS (
    SELECT [timestamp],
        LAG(quantity_closing_stock) OVER (ORDER BY timestamp)
    FROM #my_table
    WHERE quantity_closing_stock = 0

)
    UPDATE #my_table
    SET quantity_closing_stock = mycte.quantity_closing_stock - quantity
    FROM #my_table AS id
     JOIN mycte ON mycte.[timestamp] = id.[timestamp]
        
SELECT * FROM  #my_table ORDER BY timestamp ASC
yfwxisqw

yfwxisqw1#

第一行的LAG()将返回NULL,因为没有前一行,因为您的“mycte”只选择了行“WHERE quantity_closing_stock = 0”,您必须将“WHERE quantity_closing_stock = 0”从LAG()的计算中移除。

disbfnqx

disbfnqx2#

请尝试以下操作:

/* define groups using a running conditional sum window function,
   this will group quantity_closing_stock values together til a 0 value is found
*/
WITH create_groups AS
(
  SELECT *,
    SUM(CASE WHEN quantity_closing_stock=0 THEN 1 ELSE 0 END) OVER (PARTITION BY unit_id ORDER BY timestamp DESC) AS grp
  FROM table_name
),
CTE AS
(
  SELECT *,
   MAX(quantity_closing_stock) OVER (PARTITION BY unit_id, grp) - 
   SUM(quantity) OVER (PARTITION BY unit_id, grp) AS val
  FROM create_groups
)
UPDATE CTE
SET quantity_closing_stock = val
WHERE quantity_closing_stock = 0;

See demo

相关问题