【发布时间】:2021-05-01 21:44:20
【问题描述】:
我已经解决了这个问题并寻找了类似的线程,但还没有找到任何解决方案。
我尝试了几种方法,我将解释并举例说明数据和需要实现的目标:
我有一张像这样的表:
代码:
drop table if exists #temp
create table #temp
(
col1 varchar(10),
col2 varchar(10),
col3 varchar(10),
[date] date,
dateindex int,
totals money,
adjustement money
)
insert into #temp
values ('customer1', 'customer1', 'customer1', '01-01-2020', 1, 0, 100),
('customer1', 'customer1', 'customer1', '01-02-2020', 1, 0, 200),
('customer1', 'customer1', 'customer1', '01-03-2020', 1, 50, 0),
('customer1', 'customer1', 'customer1', '01-03-2020', 2, 100, 0),
('customer2', 'customer2', 'customer2', '01-04-2020', 1, 0, 150),
('customer2', 'customer2', 'customer2', '01-05-2020', 2, 0, 300),
('customer2', 'customer2', 'customer2', '01-06-2020', 1, 50, 0),
('customer2', 'customer2', 'customer2', '01-06-2020', 2, 100, 0)
我们有两个数字列:totals 和 adjustments,其余的是客户和日期的唯一属性。
当调整不为 0 时,这很好,我们不需要更改这些数字。
当总计不为 0 时,即我想要进行计算并希望更新同一行中 Adjustments 列的结果(当总计为 0 时,调整始终 = 0)。
替换那些 0 调整的计算应该是:当前总值 - 所有以前的调整(运行总计)
这是我尝试过的:
select
*,
case
when totals <> 0
then totals - sum(adjustement) over (partition by col1,col2,col3
order by [date] asc, dateindex asc
rows between unbounded preceding and 1 preceding)
else adjustement
end as 'Calculation'
from
#temp
第 3 行返回正确的结果:50 - 300 = -250
现在,当您在同一天(第 3 行和第 4 行)、同一日期但不同的索引(用于知道哪个交易先出现的索引)有总计时,窗口函数正在执行 row4 = 100 -(100+200+ 0) =-200 当它需要为 100 - (100+200-250+0) = 50 时。
不包括前面的-250,因为它不是实际数据。我需要在计算时找到更新表格的方法,以便在移动下一行之前可以在表格上更新-250。
这个计算是针对每个客户完成的,这就是我按客户列进行分区的原因。
我非常感谢任何关于这方面的提示或建议,以及什么是最好的方法
谢谢!
【问题讨论】:
-
当您的公式为
the current total value - all previous adjustments时,为什么第 1 行和第 2 行是正值? -
你的意思是把
case when放在sum的里面吗? -
这真的很奇怪。您在同一天可能有多少个值?
-
Squirrel ,因为 else 条件。它只是把已经存在的东西放在那里。
-
@GordonLinoff 同一天的总数不超过 3 个。并且它们总是被索引为 1,2,3 。
标签: sql sql-server tsql sql-server-2016 common-table-expression