2017-03-28 85 views
1

我想弄清楚如何做一种“消费”查询,其中INT值列(X)从另一个INT列(Y)中减去,直到它达到0,然后停止。 DesiredResult和DesiredResultExplanation这一列仅用于参考正在执行的数学。这发生在DESC日期顺序(未来消耗回当前)从2栏消费值

我最初的方法是使用窗口功能,但问题是一旦值(Y)达到0,它需要停止执行运行总数。使用CTE也有类似的问题。

如果更改表格结构将有所帮助,可以这样做。

版本:SQL Server 2014或更高版本

谢谢!

DECLARE @test TABLE 
(
ID INT IDENTITY (1,1) 
,PeriodDate DATE 
,X INT 
,Y INT 
,DesiredResult INT 
,DesiredResultExplanation VARCHAR(100) 
) 

INSERT INTO @test VALUES ('2017-05-01', 100,0, 100,'Nothing left to subtract. Value is unchanged') 
INSERT INTO @test VALUES ('2017-05-08', 200,0, 200,'Nothing left to subtract. Value is unchanged') 
INSERT INTO @test VALUES ('2017-05-15', 300,0, 100,'300 - 200 = 100 (Orig -1100 has been consumed)') 
INSERT INTO @test VALUES ('2017-05-22', 400,0,-200,'400 - 600 = -200 ') 
INSERT INTO @test VALUES ('2017-05-29', 500,-1100,-600, '500 - 1100 = -600') 

SELECT * 
FROM @test 
ORDER BY PeriodDate DESC 
+0

不知道什么是'没有什么可以减少',突然你减少。因为在您的示例中,列'Y'不会更改 –

+0

请按照DESC顺序查看列PeriodDate。 1100在5/29被消耗并且向后移动。当它达到5/8和5/1时,1100被消耗。希望有道理 – Kirby1367

+0

1100哪里来? –

回答

3

DEMO

WITH cte as (
    SELECT *, 
      SUM(X) OVER (ORDER BY PeriodDate DESC) accumulated 
    FROM @test 
), parameter as (
    SELECT 1100 as startY 
)  
SELECT *, 
     CASE WHEN accumulated <= startY 
      THEN accumulated - startY 
      WHEN LAG(accumulated) OVER (ORDER BY PeriodDate DESC) < startY 
      THEN accumulated - startY 
      ELSE X 
     END as newDesire 
FROM cte 
CROSS JOIN parameter 
ORDER BY PeriodDate DESC; 

输出

​​

编辑:您可以更改LAG条件与

WHEN accumulated - X < startY 
+0

我忘了使用LAG!这是我需要的基础。谢谢胡安! – Kirby1367

+0

好,如果你看到的关键是使用comulative'SUM'编辑我选择删除'LAG'并认为很容易阅读 –