次の課題に直面しています。同じ列でテーブルデータを2回ローテーションする必要があります。これがデータのスクリーンショットです。
各年の購入値と販売値の両方を含むアイテムIDごとに1つの行が必要です。 「年」列を2回選択し、各販売年の先頭に「S」が付き、各購入年が「P」で始まるように少しフォーマットし、2つのピボットを使用して2年の列を回転させて、これを試みました。以下はSQLクエリです(SQL Server 2008で使用)。
SELECT [Item ID],
[P2000],[P2001],[P2002],[P2003],
[S2000],[S2001],[S2002],[S2003]
FROM
(
SELECT [Item ID]
,'P' + [Year] AS YearOfPurchase
,'S' + [Year] AS YearOfSelling
,[Purchasing value]
,[Selling value]
FROM [ItemPrices]
) AS ALIAS
PIVOT
(
MIN ([Purchasing value]) FOR [YearOfPurchase] in ([P2000],[P2001],[P2002],[P2003])
)
AS pvt
PIVOT
(
MIN ([Selling value]) FOR [YearOfSelling] in ([S2000],[S2001],[S2002],[S2003])
)
AS pvt2
結果は私が望んでいたものとは正確には異なります(下の画像を参照)。
ご覧のとおり、各アイテムIDにはまだ複数の行があります。行数をアイテムごとに正確に1つに減らす方法はありますか?以下のExcelスクリーンショットのように見えるようにするには?
私の提案は、結果を得るためにUNPIVOT
関数とPIVOT
関数の両方を適用することです。
UNPIVOT
は、PurchasingValue
およびSellingValue
列を行に変換します。これが完了すると、データを結果にピボットできます。
コードは次のようになります。
select *
from
(
select itemid,
case
when col = 'PurchasingValue' then 'P'
when col = 'SellingValue' then 'S'
end + cast(year as varchar(4)) new_col,
value
from yourtable
unpivot
(
value
for col in ([PurchasingValue], [SellingValue])
) unpiv
) src
pivot
(
max(value)
for new_col in (P2000, P2001, P2002, P2003,
S2000, S2001, S2002, S2003)
) piv;
SQL Fiddle with Demo を参照してください。結果は次のとおりです。
| ITEMID | P2000 | P2001 | P2002 | P2003 | S2000 | S2001 | S2002 | S2003 |
--------------------------------------------------------------------------
| 1 | 1000 | 1100 | 1200 | 1300 | 900 | 990 | 1080 | 1170 |
| 2 | 500 | 550 | 600 | 650 | 450 | 495 | 540 | 585 |
SQL Server 2008以降では、CROSS APPLY
with VALUES
with PIVOT
function:
select *
from
(
select itemid,
col+cast(year as varchar(4)) new_col,
value
from yourtable
cross apply
(
VALUES
(PurchasingValue, 'P'),
(SellingValue, 'S')
) x (value, col)
) src
pivot
(
max(value)
for new_col in (P2000, P2001, P2002, P2003,
S2000, S2001, S2002, S2003)
) piv
複数の列をピボットする簡単な方法の1つは、Aggregate(Case)式を使用することです。
SELECT [Item ID],
[P2000] = SUM(CASE WHEN [Year] = 2000 THEN [Purchasing value] END),
[P2001] = SUM(CASE WHEN [Year] = 2001 THEN [Purchasing value] END),
[P2002] = SUM(CASE WHEN [Year] = 2002 THEN [Purchasing value] END),
[P2003] = SUM(CASE WHEN [Year] = 2003 THEN [Purchasing value] END),
[S2000] = SUM(CASE WHEN [Year] = 2000 THEN [Selling value] END),
[S2001] = SUM(CASE WHEN [Year] = 2001 THEN [Selling value] END),
[S2002] = SUM(CASE WHEN [Year] = 2002 THEN [Selling value] END),
[S2003] = SUM(CASE WHEN [Year] = 2003 THEN [Selling value] END)
FROM ItemPrices
GROUP BY [Item ID]
各結果列で集約関数SUM(isnull(value、0))を使用してGROUP BY ItemIDを使用します。