2013-03-13 50 views
0

我有2個表,T1T2。我想要加入這兩個表並只返回2行數據,用T2的查找值替換Item中的整數。用查找表中的值重組連接列表

T1

Item Date 
------ --------- 
1;4;5; 3/13/2013 
1;2;3; 3/13/2013 

T2

ID Desc 
---- ------ 
1  Tree 
2  Grass 
3  Sand 
4  Water 
5  Bridge 

預期結果:

Item     Date 
------------------ --------- 
Tree;Water;Bridge; 3/13/2013 
Tree;Grass;Sand;  3/13/2013 

回答

2

首先,創建它返回一個整數和一個保持順序的序列號的分割功能。這裏有一個例子:

ALTER FUNCTION dbo.SplitInts 
(
    @List  VARCHAR(MAX), 
    @Delimiter VARCHAR(32) 
) 
RETURNS TABLE 
AS 
    RETURN 
    (
     SELECT rn = ROW_NUMBER() OVER (ORDER BY Number), 
     Item = CONVERT(INT, Item) 
     FROM (SELECT Number, Item = LTRIM(RTRIM(SUBSTRING(@List, Number, 
      CHARINDEX(@Delimiter, @List + @Delimiter, Number) - Number))) 
     FROM (SELECT ROW_NUMBER() OVER (ORDER BY [object_id]) 
      FROM sys.all_objects) AS n(Number) 
     WHERE Number <= CONVERT(INT, LEN(@List)) 
     AND SUBSTRING(@Delimiter + @List, Number, 1) = @Delimiter 
    ) AS y 
    ); 
GO 

則下面的查詢做你以後:

DECLARE @t1 TABLE 
(
Item VARCHAR(MAX), 
[Date] DATE -- terrible column name! 
); 

INSERT @t1 VALUES('1;4;5;','20130313'),('1;2;3;','20130313'); 
-- please use unambiguous date formats! 

DECLARE @t2 TABLE 
(
ID INT, -- another bad column name - what kind of ID? 
[Desc] VARCHAR(255) -- another bad column name, this is a keyword! 
); 

INSERT @t2 VALUES(1,'Tree'),(2,'Grass'), 
(3,'Sand'),(4,'Water'),(5,'Bridge'); 

;WITH x AS 
(
    SELECT t1.Item, Date, t2ID = i.Item, i.rn, n = t2.[Desc] 
    FROM @t1 AS t1 CROSS APPLY dbo.SplitInts(t1.Item, ';') AS i 
    INNER JOIN @t2 AS t2 ON i.Item = t2.ID 
) 
SELECT DISTINCT Item = (
    SELECT n + ';' FROM x AS x2 
    WHERE x.Item = x2.Item 
    ORDER BY x2.rn FOR XML PATH, TYPE 
).value('.[1]', 'varchar(max)'), [Date] 
FROM x; 

強烈建議您查找正常化。以分號分隔的列表是將獨立值粘合在一起的可怕方法。