如何PIVOT列标题 - SQL数据

时间:2014-01-29 22:10:38

标签: sql-server sql-server-2008-r2 pivot

我有一个需要旋转的数据集视图,因此AMC1,AMC2和AMC3的列标题将成为LOB下的行。以下是原始的例子:

 Qtr    Year    BU  BU_Description  P2A_Line       AMC1  AMC2   AMC3
 Q3 2013    B52100  52100 - UFC      L1_1          203    17     7
 Q3 2013    B52100  52100 - UFC      L1_2          -      -      -   
 Q3 2013    B52100  52100 - UFC      L1_3          123    113    -   

以下是最终结果的示例:

 Qtr    Year    BU  BU_Description   LOB     L1_1   L1_2    PL1_3
  Q3    2013    B52100  52100 - UFC  AMC1    203     -       123 
  Q3    2013    B52100  52100 - UFC  AMC2    17      -       113 
  Q3    2013    B52100  52100 - UFC  AMC3    7       -       -   

有没有人有一个简单而相对简单的方法来做到这一点?那里的例子有太多的变量来得出答案。任何帮助将不胜感激?

1 个答案:

答案 0 :(得分:2)

通过使用带有CASE表达式的聚合函数,使用PIVOT函数,有几种不同的方法可以获得结果 - 但在实现这些方法之前,首先需要查看对多列数据进行取消 - { {1}},AMC1AMC2

univoting过程将您的多列转换为行。您可以使用unpivot功能,也可以使用AMC3转换数据:

CROSS APPLY

SQL Fiddle with Demo。数据采用此格式后,您可以将select qtr, year, bu, bu_description, p2a_line, lob, value from yourtable cross apply ( select 'amc1', amc1 union all select 'amc2', amc2 union all select 'amc3', amc3 ) c (lob, value); 值转换为列。

使用带有CASE表达式的聚合函数,查询将为:

P2A_Line

请参阅SQL Fiddle with Demo

在SQL Server 2005+中,您可以使用PIVOT函数:

select qtr, year, bu, bu_description,
  lob, 
  max(case when p2a_line = 'L1_1' then value end) L1_1,
  max(case when p2a_line = 'L1_2' then value end) L1_2,
  max(case when p2a_line = 'L1_3' then value end) L1_3
from 
(
  select qtr, year, bu, bu_description, p2a_line,
    lob, value
  from yourtable
  cross apply
  (
    select 'amc1', amc1 union all
    select 'amc2', amc2 union all
    select 'amc3', amc3
  ) c (lob, value)
) d
group by qtr, year, bu, bu_description, lob;

SQL Fiddle with Demo

最后,如果您有一个未知数量的select qtr, year, bu, bu_description, lob, L1_1, L1_2, L1_3 from ( select qtr, year, bu, bu_description, p2a_line, lob, value from yourtable cross apply ( select 'amc1', amc1 union all select 'amc2', amc2 union all select 'amc3', amc3 ) c (lob, value) ) d pivot ( max(value) for p2a_line in (L1_1, L1_2, L1_3) ) piv; 值,那么您可以使用动态SQL:

p2a_line

请参阅SQL Fiddle with Demo

所有版本都会给出结果:

DECLARE @cols AS NVARCHAR(MAX),
    @query  AS NVARCHAR(MAX)

select @cols = STUFF((SELECT  ',' + QUOTENAME(P2A_Line) 
                    from yourtable
                    group by P2A_Line
                    order by P2A_Line
            FOR XML PATH(''), TYPE
            ).value('.', 'NVARCHAR(MAX)') 
        ,1,1,'')

set @query = N'SELECT qtr, year, bu, bu_description, lob,' + @cols + N' 
            from 
            (
              select qtr, year, bu, bu_description, p2a_line,
                lob, value
              from yourtable
              cross apply
              (
                select ''amc1'', amc1 union all
                select ''amc2'', amc2 union all
                select ''amc3'', amc3
              ) c (lob, value)
            ) x
            pivot 
            (
                max(value)
                for p2a_line in (' + @cols + N')
            ) p '

execute sp_executesql @query;