25

テーブルに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

--cte / partitionでこれを達成しようとしています:

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
4

1 に答える 1

36

このデータ変換は、として知られていPIVOTます。SQL Server 2005以降には、このプロセスを実行する関数があります。:

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

SQL FiddlewithDemoを参照してください。

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 FiddlewithDemoを参照してください。

テーブルで複数の結合を使用することもできます。

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 FiddlewithDemoを参照してください

すべてのバージョンの結果は同じです。

| ROWID | FIRST |  LAST |
-------------------------
|     1 |  neil | young |
|     2 |   bob | dylan |
|     3 |   tom | petty |
于 2013-02-01T17:21:00.357 に答える