2017-04-21 36 views
-3

我有下表。如何使用Sql服务器减去动态行结果

enter image description here

在这个表月份行是动态

我想下面的输入,

enter image description here

任何人知道的解决方案,使输出。

+1

如果它有更多的行(例如100行)你的逻辑输出将如何? –

+0

你在哪里得到行C的值? –

+0

我需要获得新的行。您可以使用任何文本而不是C。月值为动态 –

回答

3

您可以使用类似:

select Month, [2017-04], [2017-03], [2017-02], [2017-01] 
from your_Table 
where Month in ('A', 'B') 

union all 

select 
    'C' 
    T1.[2017-04] - T2.[2017-04], 
    T1.[2017-03] - T2.[2017-03], 
    T1.[2017-02] - T2.[2017-02], 
    T1.[2017-01] - T2.[2017-03] 
from your_Table as T1 
    left outer join your_Table as T2 on T2.Month = 'A' 
where T1.Month = 'B' 
+0

Andy,如果桌子上有100行,这将不起作用... upvoted,因为逻辑是正确的。 –

+0

@冰塔当然不会。但OP在评论中提到,期望的结果应该是用两个指定行B和A减去数据。它看起来很奇怪 - 但这是原始要求:*“即使有100列也要减去B行 - 一行” * –

+0

是的正确。 [2017-04],[2017-03],[2017-02],[2017-01]这些值是动态的。我想减去B行 - 一行 –

0

非常奇怪的问题,而是:

SELECT Month 
    , [2017-04] 
    , [2017-03] 
    , [2017-02] 
    , [2017-01] 
FROM (
    SELECT Month 
    , [2017-04] 
    , [2017-03] 
    , [2017-02] 
    , [2017-01] 
    , 1 as mOrder 
    FROM table 
    WHERE Month in ('B','A') 
    UNION ALL 
    SELECT 'C' 
    , sum(case Month = 'A' then [2017-04]*-1 else [2017-04] end) 
    , sum(case Month = 'A' then [2017-03]*-1 else [2017-04] end) 
    , sum(case Month = 'A' then [2017-02]*-1 else [2017-04] end) 
    , sum(case Month = 'A' then [2017-01]*-1 else [2017-04] end) 
    , 2 as morder 
    FROM table 
    WHERE Month in ('B','A') 
) 
ORDER BY Month, mOrder 
0

如果我理解正确的话,您将需要动态地添加行和检查应与总是做因此我会使用以下代码:

insert into dbo.tab1 
select 'C' as month 
     , t.[2017-04] - tprev.[2017-04] as [2017-04] 
     , t.[2017-03] - tprev.[2017-03] as [2017-03] 
     , t.[2017-02] - tprev.[2017-02] as [2017-02] 
     , t.[2017-01] - tprev.[2017-01] as [2017-01] 
from ( 
     select ROW_NUMBER() OVER(ORDER BY month) AS Nr 
      , month 
      , [2017-04] 
      , [2017-03] 
      , [2017-02] 
      , [2017-01] 
     from dbo.tab1 
     ) t left join (
       select ROW_NUMBER() OVER(ORDER BY month) AS Nr 
        , month 
        , [2017-04] 
        , [2017-03] 
        , [2017-02] 
        , [2017-01] 
       from dbo.tab1 
      ) tprev on t.Nr = (tprev.Nr -1) -- join with prev row to get the difference 

您可以将此i在预先生成月份值的循环中,并在此处传递它是一个参数。 我生成了行号并加入了它,因为如果您的行数多于前两行,则需要添加一列。 你可以检查这个here的工作版本。