Alors que la réponse de M.Ali vous donnera le résultat, puisque vous utilisez SQL Server 2012, je ne ferais pas pivoter le name
et address
colonnes légèrement différentes pour obtenir le résultat final.
Puisque vous utilisez SQL Server 2012, vous pouvez utiliser CROSS APPLY
avec VALUES
pour détacher ces multiples colonnes en plusieurs lignes. Mais avant de faire cela, j'utiliserais row_number()
pour obtenir le nombre total de nouvelles colonnes que vous aurez.
Le code pour "UNPIVOT" les données à l'aide de CROSS APPLY ressemble à :
select d.loanid,
col = c.col + cast(seq as varchar(10)),
c.value
from
(
select loanid, name, address,
row_number() over(partition by loanid
order by loanid) seq
from yourtable
) d
cross apply
(
values
('name', name),
('address', address)
) c(col, value);
Voir SQL Fiddle avec démo. Cela va obtenir vos données dans un format similaire à :
| LOANID | COL | VALUE |
|--------|----------|----------|
| 1 | name1 | John |
| 1 | address1 | New York |
| 1 | name2 | Carl |
| 1 | address2 | New York |
| 1 | name3 | Henry |
| 1 | address3 | Boston |
Vous avez maintenant une seule colonne COL
avec tous vos nouveaux noms de colonne et les valeurs associées sont également dans une seule colonne. Les nouveaux noms de colonne ont maintenant un nombre à la fin (1, 2, 3, etc.) basé sur le nombre total d'entrées que vous avez par loanid
. Vous pouvez maintenant appliquer PIVOT :
select loanid,
name1, address1, name2, address2,
name3, address3
from
(
select d.loanid,
col = c.col + cast(seq as varchar(10)),
c.value
from
(
select loanid, name, address,
row_number() over(partition by loanid
order by loanid) seq
from yourtable
) d
cross apply
(
values
('name', name),
('address', address)
) c(col, value)
) src
pivot
(
max(value)
for col in (name1, address1, name2, address2,
name3, address3)
) piv;
Voir SQL Fiddle avec démo. Enfin si vous ne savez pas combien de paires de Name
et Address
vous aurez alors vous pourrez utiliser le SQL dynamique :
DECLARE @cols AS NVARCHAR(MAX),
@query AS NVARCHAR(MAX)
select @cols = STUFF((SELECT ',' + QUOTENAME(col+cast(seq as varchar(10)))
from
(
select row_number() over(partition by loanid
order by loanid) seq
from yourtable
) d
cross apply
(
select 'Name', 1 union all
select 'Address', 2
) c (col, so)
group by seq, col, so
order by seq, so
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)')
,1,1,'')
set @query = 'SELECT loanid,' + @cols + '
from
(
select d.loanid,
col = c.col + cast(seq as varchar(10)),
c.value
from
(
select loanid, name, address,
row_number() over(partition by loanid
order by loanid) seq
from yourtable
) d
cross apply
(
values
(''name'', name),
(''address'', address)
) c(col, value)
) x
pivot
(
max(value)
for col in (' + @cols + ')
) p '
exec sp_executesql @query;
Voir SQL Fiddle avec démo. Les deux versions donnent un résultat :
| LOANID | NAME1 | ADDRESS1 | NAME2 | ADDRESS2 | NAME3 | ADDRESS3 |
|--------|--------|----------|--------|----------|--------|----------|
| 1 | John | New York | Carl | New York | Henry | Boston |
| 2 | Robert | Chicago | (null) | (null) | (null) | (null) |
| 3 | Joanne | LA | Chris | LA | (null) | (null) |