如何将动态列值拆分为动态多列值

时间:2016-10-30 14:37:38

标签: sql sql-server sql-server-2012

我在将动态列值拆分为动态多列时遇到问题。

我有这样的表:

media campaign number  ---  Dynamic varchar
-----------------------------------------------------
1    --- d1:11d2:5d3:11d4:0
2    --- d1:2d2:2d3:3d4:2d5:0
3    --- d1:0d2:0d3:1d4:4d5:0d6:2d7:1

我想根据时间" dNumber"将单元格分成动态列数。出现。

结果将是:

media campaign number -- d1 - d2 - d3 - d4 - d5 - d6 - d7
1 - 11 - 5 - 11 - 0
2 - 2 - 2 - 3 - 2 - 0 
3 - 0 - 0 - 1 - 4 - 0 - 2 - 1 

知道怎么解决吗?

1 个答案:

答案 0 :(得分:2)

我怀疑你可能必须动态,除非你能定义最大列数。

以下使用Parse / Solit函数

Declare @YourTable table (ID int, [campaign number] varchar(max))
Insert Into @YourTable values
(1,'d1:11d2:5d3:11d4:0'),
(2,'d1:2d2:2d3:3d4:2d5:0'),
(3,'d1:0d2:0d3:1d4:4d5:0d6:2d7:1')

Select A.ID
      ,ColSeq   = cast(B.RetSeq-1 as varchar(25))
      ,ColValue = IIF(CharIndex('d',RetVal)=0,RetVal,Left(RetVal,CharIndex('d',RetVal)-1))
Into  #Temp
From  @YourTable A
Cross Apply (Select * from [dbo].[udf-Str-Parse](A.[campaign number],':') Where RetSeq>1) B

Declare @SQL varchar(max) = ''
Select @SQL=@SQL+',D'+ColSeq+'=max(case when ColSeq='+ColSeq+' then ColValue else null end)' 
  From (Select Top 100 Percent ColSeq from #Temp Group By ColSeq Order By cast(ColSeq as int)) A

Select @SQL = 'Select ID'+@SQL+' From #Temp Group By ID Order By ID'
Exec(@SQL)

返回

enter image description here

如果需要,可以使用解析功能

CREATE FUNCTION [dbo].[udf-Str-Parse] (@String varchar(max),@Delimiter varchar(10))
Returns Table 
As
Return (  
    Select RetSeq = Row_Number() over (Order By (Select null))
          ,RetVal = LTrim(RTrim(B.i.value('(./text())[1]', 'varchar(max)')))
    From (Select x = Cast('<x>'+ Replace(@String,@Delimiter,'</x><x>')+'</x>' as xml).query('.')) as A 
    Cross Apply x.nodes('x') AS B(i)
);