Reputation: 11273
I have been given a table of data that I need to extract and normalize. It looks like this:
AccountName BrandCoke BrandPepsi BrandDiet SalesCoke SalesPepsi SalesDiet
Account1 X X 100 200
Account2 X X 300 400
Account3 X 500
I need to normalize it, converting columns to rows like so:
AccountName Brand Sales
Account1 Coke 100
Account1 Pepsi 200
Account2 Pepsi 300
Account2 Diet 400
Account3 Coke 500
It looks like a good candidate for using UNPIVOT
, except I am unsure how to account for the fact that the brand name depends on whether there is an "X" in columns 2-4 and the fact that I only need a row for the brand if there is an "X" in that brand's column. (So only 5 rows should be generated, not 9)
My other thought was to use the SQL2000 way of doing this before UNPIVOT
and do separate SELECTS
like this:
SELECT AccountName, Brand='Coke', Sales = SalesCoke FROM T WHERE BrandCoke = 'X'
UNION
SELECT AccountName, Brand='Pepsi', Sales = SalesPepsi FROM T WHERE BrandPepsi = 'X'
UNION
SELECT AccountName, Brand='Diet', Sales = SalesDiet FROM T WHERE BrandDiet = 'X'
But that seems rather inelegant.
Can this be done easily with UNPIVOT, or is UNIONing multiple SELECTs a better solution?
Upvotes: 0
Views: 75
Reputation: 247720
Since you are using SQL Server 2008 you should be able to use CROSS APPLY with VALUES to unpivot the columns in pairs. The syntax will be:
select AccountName, Brand, Sales
from yourtable
cross apply
(
values
('Coke', BrandCoke, SalesCoke),
('Pepsi', BrandPepsi, SalesPepsi),
('Diet', BrandDiet, SalesDiet)
) c (Brand, origCol, Sales)
where origCol is not null;
Upvotes: 1