I have a table and values as shown here
create table #example(id int primary key identity, cols varchar(255))
insert into #example(cols) values('HI,HELLO,BYE,TC')
insert into #example(cols) values('WHAT,ARE,YOU,DOING,HERE')
I need the resultant output as shown in the picture
Note : There is no limit for values i.e dynamic
Use Excel Flash Fill to Split Comma Separated Values into Different Columns We can type a portion of the comma-separated data in a different column and then apply the Flash Fill feature to get the rest of the data of the same pattern. Type ‘ Dates ’ in Cell C5.
2. In the Split Cells dialog box, select Split to Rows or Split to Columns in the Type section as you need. And in the Specify a separator section, select the Other option, enter the comma symbol into the textbox, and then click the OK button. See screenshot:
Comma-separated values. A CSV file stores tabular data (numbers and text) in plain text. Each line of the file is a data record. Each record consists of one or more fields, separated by commas. The use of the comma as a field separator is the source of the name for this file format .
In computing, a comma-separated values (CSV) file is a delimited text file that uses a comma to separate values. A CSV file stores tabular data (numbers and text) in plain text. Each line of the file is a data record.
This is what you are expecting
Schema:
CREATE TABLE #EXAMPLE(ID INT PRIMARY KEY IDENTITY, COLS VARCHAR(255))
INSERT INTO #EXAMPLE(COLS) VALUES('HI,HELLO,BYE,TC')
INSERT INTO #EXAMPLE(COLS) VALUES('WHAT,ARE,YOU,DOING,HERE')
Do split those comma separated values into Rows and Apply pivot
SELECT * FROM (
SELECT id
, ROW_NUMBER() OVER(PARTITION BY ID ORDER BY (SELECT 1)) AS ID2
, SPLT.CLMS.value('.','VARCHAR(MAX)') AS LIST FROM (
select id
, CAST( '<M>'+REPLACE(cols,',','</M><M>')+'</M>' AS XML) AS XML_COL from #example E
)E
CROSS APPLY E.XML_COL.nodes('/M') AS SPLT(CLMS)
)A
PIVOT
(
MAX(LIST) FOR ID2 IN ([1],[2],[3],[4],[5])
)PV
You will get result as
+----+------+-------+-----+-------+------+
| id | 1 | 2 | 3 | 4 | 5 |
+----+------+-------+-----+-------+------+
| 1 | HI | HELLO | BYE | TC | NULL |
| 2 | WHAT | ARE | YOU | DOING | HERE |
+----+------+-------+-----+-------+------+
Edit:
And now you need to go for dynamic pivot,since There is no limit for values.
DECLARE @COLS VARCHAR(MAX)='', @QRY VARCHAR(MAX)='';
SELECT @COLS =@COLS+'['+CAST( ID2 AS VARCHAR(10))+'],' FROM (
SELECT DISTINCT ROW_NUMBER() OVER(PARTITION BY ID ORDER BY (SELECT 1)) AS ID2 FROM (
select id, CAST( '<M>'+REPLACE(cols,',','</M><M>')+'</M>' AS XML) AS XML_COL from #example E
)E
CROSS APPLY E.XML_COL.nodes('/M') AS SPLT(CLMS)
)A
SELECT @COLS = LEFT(@COLS,LEN(@COLS)-1)
SELECT @QRY =
'
SELECT * FROM (
SELECT id
, ROW_NUMBER() OVER(PARTITION BY ID ORDER BY (SELECT 1)) AS ID2
, SPLT.CLMS.value(''.'',''VARCHAR(MAX)'') AS LIST FROM (
select id, CAST( ''<M>''+REPLACE(cols,'','',''</M><M>'')+''</M>'' AS XML) AS XML_COL from #example E
)E
CROSS APPLY E.XML_COL.nodes(''/M'') AS SPLT(CLMS)
)A
PIVOT
(
MAX(LIST) FOR ID2 IN ('+@COLS+ ')
)PV'
EXEC( @QRY)
Dynamic version base on split string
then pivot
table
Schema:
create table #example(id int primary key identity, cols varchar(255))
insert into #example(cols) values('HI,HELLO,BYE,TC')
insert into #example(cols) values('WHAT,ARE,YOU,DOING,HERE')
Calculate columns pivot
-- Calculate dynamic columns
;WITH temps AS
(
SELECT sd.* ,CAST('<x>' + replace(sd.cols, ',', '</x><x>') + '</x>' as xml) AS xmlText
FROM #example sd
),
temps1 AS
(
SELECT t.Id, t.cols, v.x.value('.','varchar(50)') AS Value
FROM temps t
CROSS APPLY
t.xmlText.nodes('/x') AS v(x)
)
SELECT @ColumnPivot = STUFF((SELECT DISTINCT CONCAT(',COL',row_number() OVER(PARTITION BY t.id ORDER BY t.Value)) FROM temps1 t FOR XML PATH('')), 1,1,'')
PRINT @ColumnPivot
Then PIVOT
table
DECLARE @query nvarchar(max) =
CONCAT(N';WITH temps AS
(
SELECT sd.* ,CAST(''<x>'' + replace(sd.cols, '','', ''</x><x>'') + ''</x>'' as xml) AS xmlText
FROM #example sd
),
temps1 AS
(
SELECT t.Id, t.cols, v.x.value(''.'' , ''varchar(50)'') AS Value
FROM temps t
CROSS APPLY
t.xmlText.nodes(''/x'') AS v(x)
),
temps2 AS
(
SELECT t.* , CONCAT(''COL'',row_number() OVER(PARTITION BY t.id ORDER BY (select 1))) AS ColGroup
FROM temps1 t
)',
N'SELECT Id, cols, ' , @ColumnPiVot,
' FROM
(
select * from temps2
) AS src
PIVOT
(MAX(Value) FOR ColGroup IN (',@ColumnPiVot,')) AS pvt')
PRINT @query
exec sp_executesql @query
DROP TABLE #example
Demo link: Rextester
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With