I have a table in Microsoft SQL Server like the following:
Main_Key | IDx | IDy | IDz | Count |
---|---|---|---|---|
123450 | 0 | 0 | 0 | 0 |
123450 | 0 | 0 | 1 | 1 |
123450 | 0 | 0 | 2 | 0 |
123450 | 0 | 0 | 3 | 5 |
123450 | 1 | 0 | 0 | 4 |
123450 | 1 | 0 | 1 | 3 |
123450 | 1 | 0 | 2 | 8 |
123450 | 1 | 0 | 3 | 0 |
123450 | 0 | 1 | 0 | 5 |
123450 | 0 | 1 | 1 | 6 |
123450 | 0 | 1 | 2 | 0 |
123450 | 0 | 1 | 3 | 0 |
123450 | 1 | 1 | 0 | 6 |
123450 | 1 | 1 | 1 | 2 |
123450 | 1 | 1 | 2 | 3 |
123450 | 1 | 1 | 3 | 1 |
123450 | 0 | 2 | 0 | 4 |
123450 | 0 | 2 | 1 | 5 |
123450 | 0 | 2 | 2 | 0 |
123450 | 0 | 2 | 3 | 7 |
123450 | 1 | 2 | 0 | 9 |
123450 | 1 | 2 | 1 | 9 |
123450 | 1 | 2 | 2 | 2 |
123450 | 1 | 2 | 3 | 5 |
123451 | ... | ... | ... | ... |
- ID1 can be 0 or 1.
- ID2 can be 0, 1, or 2.
- ID3 can be 0, 1, 2, or 3.
I want to unpivot this like the following table:
Main_Key | ID_Type | Count |
---|---|---|
123450 | IDx_0_IDy_0 | 6 |
123450 | IDx_1_IDy_0 | 12 |
123450 | IDx_0_IDy_1 | 11 |
123450 | IDx_1_IDy_1 | 12 |
123450 | IDx_0_IDy_2 | 16 |
123450 | IDx_1_IDy_2 | 25 |
123450 | IDx_0_IDz_0 | 20 |
As you can see, what I like to see is that I want to create a cross tab between different values of each ID. In fact, in the ID_Type column, whenever one sees a ID like IDx_a_IDy_b with the Main_Key = ZZZ, the count variable will be the sum of the count variables for all the rows having Main_Key = ZZZ and IDx = a and IDy = b (a 2x2 grid between each two IDs).
I already solved this by first creating the grid by many "CASE" conditions:
select
main_key,
sum(case when IDx = 0 and IDy = 0 then count else 0 end) as IDx_0_IDy_0,
sum(case when IDx = 1 and IDy = 0 then count else 0 end) as IDx_1_IDy_0,
sum(case when IDx = 0 and IDy = 1 then count else 0 end) as IDx_0_IDy_1,
from
table
group by
main_key
and then unpivot this either using the "UNPIVOT" method or "UNION ALL" method. However, this method takes a very long time, especially with the fact that there will be like 15 million records in my table. Is there any built-in method in SQL that can do such a thing? or make this query faster? Much appreciated :)