我正在寻求有关计算SQL(Microsoft SQL Server)组中连续有序行之间差异的帮助。
我有一张这样的桌子:
ID School_ID Enrollment_Start_Date Order
1 56 1/1/2018 10
1 56 5/5/2018 24
1 56 7/7/2018 35
1 103 4/4/2019 26
1 103 3/3/2019 19
我想计算订购,分组依据 ID,学校ID和订购依据注册日期之间的差异。
所以我想要这样的东西:
ID School_ID Enrollment_Start_Date Order Diff
1 56 1/1/2018 10 10 # nothing to be subtracted from 10
1 56 5/5/2018 24 14 # 24-10
1 56 7/7/2018 35 11 # 35-24
1 103 3/3/2019 19 19 # nothing to be subtracted from 19
1 103 4/4/2019 26 7 # 26-19
我有数百个ID,每个ID最多可以有6个Enrollment_Start_Date,因此我正在寻找一些可概括的实现。
答案 0 :(得分:2)
使用LAG(<column>)
分析函数获得在OVER
部分中指定的“上一个”列值,然后从中减去当前值,并使其为正数乘以-1
。如果以前的值不存在(为null),则取当前值。
伪代码为:
If previous_order_value exists:
-1 * (previous_order_value - current_order_value)
Else
current_order_value
其中previous_order_value基于相同的ID和school_id,并按enrollment_start_date升序排序
SQL代码:
select
id,
school_id,
enrollment_start_date,
[order],
coalesce(-1 * (lag([order]) over (partition by id, school_id order by enrollment_start_date ) - [order]), [order]) as diff
from yourtable
还请注意,order
关键字在SQL Server中是保留的,这就是为什么您创建的列的名称包含在[ ]
中的原因。如果可能,我建议在此列中使用其他词语。
答案 1 :(得分:1)
使用lag()
分析函数获取两行之间的差异,并获取不存在差异的订单列原始值的情况
with cte as
(
select 1 as id, 56 as sclid, '2018-01-01' as s_date, 10 as orders
union all
select 1,56,'2018-05-05',24 union all
select 1,56,'2018-07-07',35 union all
select 1,103,'2019-04-04',26 union all
select 1,103,'2019-03-03',19
) select t.*,
case when ( lag([orders])over(partition by id,sclid order by s_date ) -[orders] )
is null then [orders] else
( lag([orders])over(partition by id,sclid order by s_date ) -[orders] )*(-1) end
as diff
from cte t
输出
id sclid s_date orders diff
1 56 2018-01-01 10 10
1 56 2018-05-05 24 14
1 56 2018-07-07 35 11
1 103 2019-03-03 19 19
1 103 2019-04-04 26 7
答案 2 :(得分:0)
使用LAG(COLUMN_NAME)
查询
SELECT id, School_ID, Enrollment_Start_Date, cOrder,
ISNULL((cOrder - (LAG(cOrder) OVER(PARTITION BY id, School_ID ORDER BY Enrollment_Start_Date))),cOrder)Diff
FROM Table1
样本输出
| id | School_ID | Enrollment_Start_Date | cOrder | Diff |
|----|-----------|-----------------------|--------|------|
| 1 | 56 | 2018-01-01 | 10 | 10 |
| 1 | 56 | 2018-05-05 | 24 | 14 |
| 1 | 56 | 2018-07-07 | 35 | 11 |
| 1 | 103 | 2019-03-03 | 19 | 19 |
| 1 | 103 | 2019-04-04 | 26 | 7 |