我正在尝试使用我拥有的三个表,并以用户要求我这样做的方式显示数据。表格看起来像这样。 (我应该补充说我正在使用MS SQL Server)
第一张表:ID是varchar,因为它是用于识别资产的ID,它们使用数字和字母。
aID| status | group |
-----------------------
1 | acti | group1 |
2 | inac | group2 |
A3 | acti | group1 |
第二张表:此表已修复。它有大约20个值,ID都是数字
atID| traitname |
------------------
1 | trait1 |
2 | trait2 |
3 | trait3 |
第三表:该表用于识别第一个表中资产的特征。与上表中的字段同名的字段显然是链接的。
tID| aID | atID | trait |
----------------------------------
1 | 1 | 1 | NAME |
2 | 1 | 2 | INFO |
3 | 2 | 3 | GOES |
4 | 2 | 1 | HERE |
5 | A3 | 2 | HAHA |
现在,用户希望程序以下列格式输出数据:
aID| status | group | trait1 | trait2 | trait 3
-------------------------------------------------
1 | acti | group1 | NAME | INFO | NULL
2 | inac | group2 | HERE | NULL | GOES
A3 | acti | group1 | NULL | HAHA | NULL
我明白要实现这一点,我必须在SQL中使用Pivot命令。但是,我已阅读并试图理解它,但我似乎无法得到它。特别是它要求MAX值的部分。我不明白为什么我需要那个MAX。
此外,我见过的例子是一张桌子。我不确定我是否可以用三张桌子来做。我确实有一个查询,将所有这三个与我需要的信息连接起来。但是,我不知道如何从那里开始。对此,任何帮助将不胜感激。谢谢。
答案 0 :(得分:4)
有几种方法可以获得结果,包括使用PIVOT功能。
您可以将聚合函数与CASE表达式一起使用:
select t1.aid, t1.status, t1.[group],
max(case when t2.traitname = 'trait1' then t3.trait end) trait1,
max(case when t2.traitname = 'trait2' then t3.trait end) trait2,
max(case when t2.traitname = 'trait3' then t3.trait end) trait3
from table1 t1
inner join table3 t3
on t1.aid = t3.aid
inner join table2 t2
on t3.atid = t2.atid
group by t1.aid, t1.status, t1.[group];
PIVOT函数需要一个聚合函数,这就是你需要使用MIN或MAX函数的原因(因为你有一个字符串值)。
如果您的traitnames
数量有限,那么您可以对查询进行硬编码:
select aid, status, [group],
trait1, trait2, trait3
from
(
select t1.aid,
t1.status,
t1.[group],
t2.traitname,
t3.trait
from table1 t1
inner join table3 t3
on t1.aid = t3.aid
inner join table2 t2
on t3.atid = t2.atid
) d
pivot
(
max(trait)
for traitname in (trait1, trait2, trait3)
) piv;
如果您有未知数量的值,那么您将需要查看使用动态SQL来获得最终结果:
DECLARE @cols AS NVARCHAR(MAX),
@query AS NVARCHAR(MAX)
select @cols = STUFF((SELECT distinct ',' + QUOTENAME(traitname)
from Table2
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)')
,1,1,'')
set @query = 'SELECT aid, status, [group],' + @cols + '
from
(
select t1.aid,
t1.status,
t1.[group],
t2.traitname,
t3.trait
from table1 t1
inner join table3 t3
on t1.aid = t3.aid
inner join table2 t2
on t3.atid = t2.atid
) x
pivot
(
max(trait)
for traitname in (' + @cols + ')
) p '
execute sp_executesql @query;