我有一个大问题,必须显示多个labels
。
DECLARE @Example TABLE
(
[ID] INT IDENTITY(1,1)
,[CountryID] INT
,[Choise_1_id] INT
,[Choise_2_id] INT
,[Choise_3_id] INT
,[Choise_4_id] INT
,[Choise_5_id] INT
);
INSERT INTO @Example ([CountryID], [Choise_1_id], [Choise_2_id], [Choise_3_id], [Choise_4_id], [Choise_5_id])
VALUES (101, 1, 2, 3, 4, 5)
,(102, 2, 3, NULL, NULL, NULL)
,(103, 5, 2, 4, NULL, NULL)
,(104, 3, 2, 4, 1, 5);
DECLARE @LableLookup TABLE
(
[Label_ID] INT IDENTITY(1,1)
,[Value] VARCHAR(50)
);
INSERT INTO @LableLookup ([Value])
VALUES ('Test 1')
,('Test 2')
,('Test 3')
,('Test 4')
,('Test 5');
我必须显示每个标签,因此查询如下:
SELECT l1.Value,l2.Value,l3.Value,l4.Value,l5.Value
FROM @Example E
LEFT JOIN @LableLookup l1 ON l1.Label_ID = E.CountryId
LEFT JOIN @LableLookup l2 ON l2.Label_ID = E.Choise_1_id
LEFT JOIN @LableLookup l3 ON l3.Label_ID = E.Choise_2_id
LEFT JOIN @LableLookup l4 ON l4.Label_ID = E.Choise_3_id
LEFT JOIN @LableLookup l5 ON l5.Label_ID = E.Choise_4_id
...
有更好的方法吗?
我不想扫描每列的LabelLookup
表。
表格中可能有数十Choise_ids
。
答案 0 :(得分:1)
如果您在LabelLookup(Labeld)
上有索引(如果您修复了join
条件),那么您的代码应该相当有效。
但是,如果一行中有多个列通常是一个坏主意,其唯一的区别特征是最后的数字。
相反,您需要另一个表,每个CountryId
和ChoiseId
的行 - 以及其他可能表示排序的信息。
答案 1 :(得分:1)
您可以使用LEFT JOIN
和UNPIVOT
条款替换多个INNER JOIN
子句:
DECLARE @DataSource TABLE
(
[ID] INT IDENTITY(1,1)
,[CountryID] INT
,[Choise_1_id] INT
,[Choise_2_id] INT
,[Choise_3_id] INT
,[Choise_4_id] INT
,[Choise_5_id] INT
);
INSERT INTO @DataSource ([CountryID], [Choise_1_id], [Choise_2_id], [Choise_3_id], [Choise_4_id], [Choise_5_id])
VALUES (101, 1, 2, 3, 4, 5)
,(102, 2, 3, NULL, NULL, NULL)
,(103, 5, 2, 4, NULL, NULL)
,(104, 3, 2, 4, 1, 5);
DECLARE @LableLookup TABLE
(
[LabelID] INT IDENTITY(1,1)
,[Value] VARCHAR(50)
);
INSERT INTO @LableLookup ([Value])
VALUES ('Test 1')
,('Test 2')
,('Test 3')
,('Test 4')
,('Test 5');
SELECT *
FROM @DataSource
UNPIVOT
(
[LabelID] FOR [Choise] IN ([Choise_1_id], [Choise_2_id], [Choise_3_id], [Choise_4_id], [Choise_5_id])
) UNPVT
INNER JOIN @LableLookup LL
ON UNPVT.[LabelID] = LL.[LabelID];
结果如下:
如果您不需要这种格式,则可以继续操作结果集。