varchar的{Pivot列}

时间:2015-12-18 17:03:03

标签: sql sql-server

我试图在表中包含一些数据,但是我不能这样做,因为我找不到使用varchar列的方法。我有这张桌子:

declare @table  table(name VARCHAR(50) not null, occupation VARCHAR(MAX))

insert into @table values ('A','Doctor')
insert into @table values ('B','Doctor')
insert into @table values ('A','Professor')
insert into @table values ('A','Singer')
insert into @table values ('A','Actor')

SELECT 

CASE WHEN occupation = 'Doctor' THEN NAME END AS Doctor,
CASE WHEN occupation = 'Professor' THEN NAME END AS Professor,
CASE WHEN occupation = 'Singer' THEN NAME END AS Singer,
CASE WHEN occupation = 'Actor' THEN NAME END AS Actor
FROM @table

输出:

Doctor  Professor   Singer  Actor
A   NULL    NULL    NULL
B   NULL    NULL    NULL
NULL    A   NULL    NULL
NULL    NULL    A   NULL
NULL    NULL    NULL    A

对于Pivot,我得到了这个输出:

select * from 
(
select name, occupation from @table ) src
pivot (
min(name)
for occupation in ([Doctor],[Professor],[Singer],[Actor])) as pvt

Doctor  Professor   Singer  Actor
A        A          A       A   

对于min / max / function,pivot函数只给我部分输出,对于count函数,我得到医生,歌手等的记录数。但是我需要实际行,而不是行数。

我需要的是:

Doctor  Professor   Singer  Actor
A        A          A       A   
B       NULL        NULL    NULL

即假设我们有5个医生姓名,我们需要显示5个医生栏目。

1 个答案:

答案 0 :(得分:1)

您可以按照建议使用PIVOT,只需使用ROW_NUMBER添加列:

SELECT [Doctor],[Professor],[Singer],[Actor]
FROM (SELECT name, occupation,
             rn = ROW_NUMBER() OVER (PARTITION BY occupation ORDER BY occupation) 
      FROM @table ) AS src
PIVOT (
  MIN(name)
  FOR occupation IN ([Doctor],[Professor],[Singer],[Actor])
) AS pvt

LiveDemo

输出:

╔════════╦═══════════╦════════╦═══════╗
║ Doctor ║ Professor ║ Singer ║ Actor ║
╠════════╬═══════════╬════════╬═══════╣
║ A      ║ A         ║ A      ║ A     ║
║ B      ║           ║        ║       ║
╚════════╩═══════════╩════════╩═══════╝

修改

您没有编写如何处理更多行,因此请考虑这种情况。 以上解决方案将返回:

╔════════╦═══════════╦════════╦═══════╗
║ Doctor ║ Professor ║ Singer ║ Actor ║
╠════════╬═══════════╬════════╬═══════╣
║ A      ║ A         ║ A      ║ A     ║
║ B      ║           ║ C      ║       ║
╚════════╩═══════════╩════════╩═══════╝

VS

╔════════╦═══════════╦════════╦═══════╗
║ Doctor ║ Professor ║ Singer ║ Actor ║
╠════════╬═══════════╬════════╬═══════╣
║ A      ║ A         ║ A      ║ A     ║
║ B      ║           ║        ║       ║
║        ║           ║ C      ║       ║
╚════════╩═══════════╩════════╩═══════╝

如果您想要使用第二种情况:

SELECT [Doctor],[Professor],[Singer],[Actor]
FROM (SELECT name, occupation,
             rn = DENSE_RANK() OVER (ORDER BY Name) 
      FROM @table ) AS src
PIVOT (
  MIN(name)
  FOR occupation IN ([Doctor],[Professor],[Singer],[Actor])
) AS pvt

LiveDemo2