如何计算记录之间的差异?

时间:2011-10-31 06:56:35

标签: sql

我的表记录如下

ym  cnt
200901  57
200902  62
200903  67
...
201001  84
201002  75
201003  75
...
201101  79
201102  77
201103  80
...

我想计算当月和每月之间的差异。 结果如下......

ym  cnt       diff
200901  57        57   
200902  62        5  (62 - 57)
200903  67        5  (67 - 62) 
...
201001  84       ...
201002  75
201003  75
...
201101  79
201102  77
201103  80
...

有谁能告诉我如何编写一个sql来获得结果并获得良好的性能?

更新

抱歉简单的话

我的解决方案是

step1: input the currentmonth data into temp table1

step2: input the permonth data into temp table2

step3: left join 2 tables to compute the result 

Temp_Table1

SELECT  (ym - 1) as ym , COUNT( item_cnt ) as cnt
FROM _table 
GROUP BY (ym - 1 ) 
order by ym

Temp_Table2

SELECT  ym ,  COUNT( item_cnt ) as cnt
FROM _table
GROUP BY ym 
order by ym



select ym , (b.cnt - a.cnt) as diff from Temp_Table2 a 
           left join Temp_Table1 b
                on a.ym = b.ym

* 如果我想比较今年和去年的月份差异 我只能将ym - 1更改为ym - 100 *

但实际上,按键分组不仅仅是ym

最多有15个密钥和最多1亿条记录

所以,我想知道一个好的解决方案可以轻松管理来源

并且表现良好。

2 个答案:

答案 0 :(得分:1)

对于MSSQL,它有一个对表的引用,因此它可能比左连接更快(可能不是),它有两个对表的引用:

-- ================
-- sample data
-- ================
declare @t table
(
    ym varchar(6),
    cnt int
)

insert into @t values ('200901', 57)
insert into @t values ('200902', 62)
insert into @t values ('200903', 67)
insert into @t values ('201001', 84)
insert into @t values ('201002', 75)
insert into @t values ('201003', 75)

-- ===========================
-- solution
-- ===========================
select
    ym2,
    diff = case when cnt1 is null then cnt2
        when cnt2 is null then cnt1
        else cnt2 - cnt1
        end
from
(
    select
        ym1 = max(case when k = 2 then ym end),
        cnt1 = max(case when k = 2 then cnt end),
        ym2 = max(case when k = 1 then ym end),
        cnt2 = max(case when k = 1 then cnt end)
    from
    (
        select 
            *, 
            rn = row_number() over(order by ym)
        from @t
    ) t1
    cross join
    (
        select k = 1 union all select k = 2
    ) t2
    group by rn + k
) t
where ym2 is not null

答案 1 :(得分:0)

  

有谁能告诉我如何编写一个sql来获得结果

绝对。只需获取具有下一个最高日期的行,然后减去。

  

并且表现良好?

没有。关系数据库实际上并不是线性遍历,即使使用索引也需要虚拟线性遍历。