2013-02-01 40 views
15

我在表中有一組具有ID的行。我試圖用多列將它壓平。我幾乎肯定我已經用cte和可能的分區來做到這一點。試圖將行平鋪到列中

我已經使用cte刪除重複的數據,我以爲我做了類似於我在這裏嘗試完成的事情。我能夠想出可行的解決方案(下面列出),但仍然覺得應該提供更優雅的解決方案。

CREATE TABLE #MyTable (RowID int , field VARCHAR(10), value VARCHAR(10)) 

INSERT INTO #MyTable (RowID, field, value) VALUES (1, 'first', 'neil') 

INSERT INTO #MyTable (RowID, field, value) VALUES (2, 'first', 'bob' ) 

INSERT INTO #MyTable (RowID, field, value) VALUES (3, 'first', 'tom' ) 

INSERT INTO #MyTable (RowID, field, value) VALUES (1, 'last', 'young') 

INSERT INTO #MyTable (RowID, field, value) VALUES (2, 'last', 'dylan') 

INSERT INTO #MyTable (RowID, field, value) VALUES (3, 'last', 'petty') 

SELECT * FROM #mytable 

--trying與CTE /分區來實現:

SELECT rowid, 
    [first] = (Select value FROM #mytable where field = 'first' and rowid = t.rowid), 
    [last] = (Select value FROM #mytable where field = 'last' and rowid = t.rowid) 
FROM #mytable t 
GROUP BY rowid 

回答

19

該數據轉化稱爲一個PIVOT。在SQL Server 2005+中有一個將執行此過程的函數。 :

select * 
from 
(
    SELECT * 
    FROM mytable 
) src 
pivot 
(
    max(value) 
    for field in (first, last) 
) piv 

參見SQL Fiddle with Demo

或者你可以使用聚合函數與CASE表達:

select rowid, 
    max(case when field = 'first' then value end) first, 
    max(case when field = 'last' then value end) last 
from MyTable 
group by rowid 

SQL Fiddle with Demo

您還可以使用多個連接上你的餐桌:

select t1.rowid, 
    t1.value first, 
    t2.value last 
from mytable t1 
left join mytable t2 
    on t1.rowid = t2.rowid 
    and t2.field = 'last' 
where t1.field = 'first' 

SQL Fiddle with Demo

結果適用於所有版本是相同的:

| ROWID | FIRST | LAST | 
------------------------- 
|  1 | neil | young | 
|  2 | bob | dylan | 
|  3 | tom | petty | 
+1

感謝這麼多。這個關鍵點絕對是我在尋找的。我曾試過,但沒有使用max()。再次感謝。 – boone

+0

@boone歡迎您! :) – Taryn

+0

非常有用的功能,謝謝 – AlexFoxGill