【问题标题】:Dynamic Pivot (row to columns)动态透视(行到列)
【发布时间】:2013-01-08 21:30:51
【问题描述】:

我有一个Table1

ID Instance Name Size Tech
 1   0       D1  123   ABC
 1   1       D2  234   CDV
 2   2       D3  234   CDV
 2   3       D4  345   SDF

我需要使用 Dynamic PIVOT 的结果集与标题一起看起来像:

ID | Instance0_Name | Instance0_Size | Instance0_Tech | Instance1_Name | Instance1_Size | Instance1_tech
1  | D1             | 123            | ABC            | D2             | 234            | CDV

任何帮助将不胜感激。使用 Sql Server 2008。

抱歉之前的帖子。

【问题讨论】:

  • 您希望ID 显示在最终结果中吗?你有不同的IDs,你想要哪一个?
  • 我刚刚意识到这一点。感谢您指出这一点。
  • 您是否希望每个单独的“ID”值都位于单独的行上,并且与该 ID 关联的所有实例都被转出?这最终会作为结果集看起来非常难看,因为命名是基于实例值的,并且实例值似乎是唯一的。这将导致每列有一个值,并且它不适用于该行的所有实例都为 NULL。根据数据集大小,您可能会遇到列限制问题。
  • 这个查询背后的想法(它也必须应用于数据库中的其他表并将它们全部组合起来)是获得一个包含数据库中所有字段的表。 RE-ENGINEER 回到格式 - 一个 CSV 文件,人们可以在其中进行自己的测试(数据透视图/图表),因为现在我没有数据库的前端。 CSV 文件会很大。 NULL 很好。列限制 - 我认为最高为 250。

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


【解决方案1】:

您想要的输出并不完全清楚,但您可以同时使用UNPIVOTPIVOT 函数来获得结果

如果您知道列数,则可以对值进行硬编码:

select *
from
(
  select id, 
    'Instance'+cast(instance as varchar(10))+'_'+col col, 
    value
  from 
  (
    select id, 
      Instance, 
      Name, 
      cast(Size as varchar(50)) Size,
      Tech
    from yourtable
  ) x
  unpivot
  (
    value
    for col in (Name, Size, Tech)
  ) u
) x1
pivot
(
  max(value) 
  for col in
    ([Instance0_Name], [Instance0_Size], [Instance0_Tech], 
     [Instance1_Name], [Instance1_Size], [Instance1_Tech], 
     [Instance2_Name], [Instance2_Size], [Instance2_Tech], 
     [Instance3_Name], [Instance3_Size], [Instance3_Tech])
) p

SQL Fiddle with Demo

然后如果你有未知数量的值,你可以使用动态sql:

DECLARE @query  AS NVARCHAR(MAX),
    @colsPivot as  NVARCHAR(MAX)

select @colsPivot = STUFF((SELECT ',' 
                      + quotename('Instance'+ cast(instance as varchar(10))+'_'+c.name)
                    from yourtable t
                    cross apply sys.columns as C
                    where C.object_id = object_id('yourtable') and
                         C.name not in ('id', 'instance')
                    group by t.instance, c.name
                    order by t.instance
            FOR XML PATH(''), TYPE
            ).value('.', 'NVARCHAR(MAX)') 
        ,1,1,'')


set @query 
  = 'select *
      from
      (
        select id, 
          ''Instance''+cast(instance as varchar(10))+''_''+col col, 
          value
        from 
        (
          select id, 
            Instance, 
            Name, 
            cast(Size as varchar(50)) Size,
            Tech
          from yourtable
        ) x
        unpivot
        (
          value
          for col in (Name, Size, Tech)
        ) u 
      ) x1
      pivot
      (
        max(value)
        for col in ('+ @colspivot +')
      ) p'

exec(@query)

SQL Fiddle with Demo

如果结果不正确,请编辑您的 OP 并发布您期望从您提供的两个 ID 中获得的结果。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-11-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多