Sqlserver
 sql >> Base de Dados >  >> RDS >> Sqlserver

Converta com eficiência linhas em colunas no sql server


Há várias maneiras de transformar dados de várias linhas em colunas.

Usando PIVOT


No SQL Server você pode usar o PIVOT função para transformar os dados de linhas em colunas:
select Firstname, Amount, PostalCode, LastName, AccountNumber
from
(
  select value, columnname
  from yourtable
) d
pivot
(
  max(value)
  for columnname in (Firstname, Amount, PostalCode, LastName, AccountNumber)
) piv;

Veja Demonstração.

Pivot com número desconhecido de columnnames


Se você tiver um número desconhecido de columnnames que você deseja transpor, então você pode usar SQL dinâmico:
DECLARE @cols AS NVARCHAR(MAX),
    @query  AS NVARCHAR(MAX)

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

set @query = N'SELECT ' + @cols + N' from 
             (
                select value, ColumnName
                from yourtable
            ) x
            pivot 
            (
                max(value)
                for ColumnName in (' + @cols + N')
            ) p '

exec sp_executesql @query;

Veja Demonstração.

Usando uma função agregada


Se você não quiser usar o PIVOT função, então você pode usar uma função agregada com um CASE expressão:
select
  max(case when columnname = 'FirstName' then value end) Firstname,
  max(case when columnname = 'Amount' then value end) Amount,
  max(case when columnname = 'PostalCode' then value end) PostalCode,
  max(case when columnname = 'LastName' then value end) LastName,
  max(case when columnname = 'AccountNumber' then value end) AccountNumber
from yourtable

Veja Demonstração.

Usando várias junções


Isso também pode ser concluído usando várias junções, mas você precisará de alguma coluna para associar cada uma das linhas que não possui em seus dados de amostra. Mas a sintaxe básica seria:
select fn.value as FirstName,
  a.value as Amount,
  pc.value as PostalCode,
  ln.value as LastName,
  an.value as AccountNumber
from yourtable fn
left join yourtable a
  on fn.somecol = a.somecol
  and a.columnname = 'Amount'
left join yourtable pc
  on fn.somecol = pc.somecol
  and pc.columnname = 'PostalCode'
left join yourtable ln
  on fn.somecol = ln.somecol
  and ln.columnname = 'LastName'
left join yourtable an
  on fn.somecol = an.somecol
  and an.columnname = 'AccountNumber'
where fn.columnname = 'Firstname'