这个问题的标题可能措辞不多,因为我发现很难简洁地解释我想要的东西,除了提供一些演示数据。
我有一个查询,它从sql表中返回以下数据:
ID Job User Amount
1 101 Bob 100
2 101 Pete 500
3 102 Bob 400
4 102 Pete 200
5 101 Pete 850
6 102 Bob 650
我想要的是查询还返回一个名为(差异)的附加字段,其中包含同一用户和作业的连续条目中的金额之间的差异。因此,我想要返回的数据如下:
ID Job User Amount Diff
1 101 Bob 100 100
2 101 Pete 500 500
3 102 Bob 400 400
4 102 Pete 200 200
5 101 Pete 850 350
6 102 Bob 650 250
在前四行中,Diff与Amount相同,因为每个是每个用户每个作业的第一个条目(因此,差异的计算参考了有效的起始数量nil)。
最后两行包含先前在表格中出现的用户和作业组合的信息,因此Diff计算如下:
Job 101 User Pete 850 - 500 = 350
Job 102 User Bob 650 - 400 = 250
我从来没有在SQL查询中比较这样的行中的数据,所以不知道从哪里开始。任何帮助将不胜感激。
加
请注意金额不是运行总额。这是对用户在每个特定工作中的输入值进行定期评估的主观评估。事实上,金额可能会从一次评估下降到下一次评估。我想要的是一个返回连续评估“金额”之间差异的查询。
替代解释
我希望在评估金额中返回历史记录。另一个例子,查看单个Job和User如下:
Job User Amount Movement
101 Bob 100 100
101 Bob 500 400
101 Bob 400 (100)
101 Bob 1,000 600
但是,根据原始示例,需要从包含许多工作和用户的表中提取此信息。
答案 0 :(得分:3)
对于SQL Server 2012,请尝试使用
这假设您的示例中的ID = 5值是错误的
每对“前一个值”
DECLARE @t TABLE (ID int, Job int, Username varchar(10), Amount int);
INSERT @t
VALUES
(1, 101, 'Bob', 100), (2, 101, 'Pete', 500), (3, 102, 'Bob', 400),
(4, 102, 'Pete', 200), (5, 101, 'Pete', 850), (6, 102, 'Bob', 650);
SELECT
t1.*,
t1.Amount - ISNULL(LAG(Amount) OVER (PARTITION BY Job, Username ORDER BY ID), 0) AS DiffAmount
FROM
@t t1
ORDER BY
t1.ID
每对“第一价值”
SELECT
t1.*,
CASE
WHEN FIRST_VALUE(t1.ID) OVER (PARTITION BY Job, Username ORDER BY ID) = t1.ID THEN t1.Amount
ELSE t1.Amount - FIRST_VALUE(t1.Amount) OVER (PARTITION BY Job, Username ORDER BY ID)
END AS DiffAmount
FROM
@t t1
ORDER BY
t1.ID