Mutiple columns with independent where clause - SQL Pivot?

后端 未结 2 1082
误落风尘
误落风尘 2021-01-22 19:07

Is it possible to take a table that is structured in the following fashion:

ID    Month     Info1 Info2
1      1          A     B
1      2          C     D
1             


        
相关标签:
2条回答
  • 2021-01-22 19:24

    You don't need multiple subqry. Answer is very easy - use set theory. From your first table ID/Month/Info1/Info2 do ID/Month + (1+2) /Info with easy union - for example:

    select ID, cast(Month as varchar(10)) + cast('_1' as varchar(10)) ComposedMonth, Info1 Info 
    from tbl
    union all
    select ID, cast(Month as varchar(10)) + cast('_2' as varchar(10)), Info2 
    from tbl
    

    Then use on this dataset (presented as view or temp table) pivot clause.

    select * 
    from vw_tbl t
    pivot (max(Info) for ComposedMonth in ([1_1], [1_2]...)) p
    -- or if you will cast month to text
    -- pivot (max(Info) for ComposedMonth in ([Jan_1], [Jan_2]...)) p
    

    Composing strings is the key for easy pivoting.

    0 讨论(0)
  • 2021-01-22 19:42

    With the updated info

    SELECT
        t.PersonID,
        JanuaryCoverage     = SUM(CASE WHEN t.RecordMonth = 1 THEN Info1 ELSE 0 END),
        FebruaryCoverage    = SUM(CASE WHEN t.RecordMonth = 2 THEN Info1 ELSE 0 END),
        MarchCoverage       = SUM(CASE WHEN t.RecordMonth = 3 THEN Info1 ELSE 0 END),
        AprilCoverage       = SUM(CASE WHEN t.RecordMonth = 4 THEN Info1 ELSE 0 END),
        MayCoverage         = SUM(CASE WHEN t.RecordMonth = 5 THEN Info1 ELSE 0 END),
        JuneCoverage        = SUM(CASE WHEN t.RecordMonth = 6 THEN Info1 ELSE 0 END),
        JulyCoverage        = SUM(CASE WHEN t.RecordMonth = 7 THEN Info1 ELSE 0 END),
        AugustCoverage      = SUM(CASE WHEN t.RecordMonth = 8 THEN Info1 ELSE 0 END),
        SeptemberCoverage   = SUM(CASE WHEN t.RecordMonth = 9 THEN Info1 ELSE 0 END),
        OctoberCoverage     = SUM(CASE WHEN t.RecordMonth = 10 THEN Info1 ELSE 0 END),
        NovemberCoverage    = SUM(CASE WHEN t.RecordMonth = 11 THEN Info1 ELSE 0 END),
        DecemberCoverage    = SUM(CASE WHEN t.RecordMonth = 12 THEN Info2 ELSE 0 END)
    FROM [VERTICALTABLE] t
    WHERE
        t.UploadID = @UploadID
        AND RecordYear = @Year
    GROUP BY t.PersonId;
    

    Use conditional aggregation:

    SELECT
        t.ID,
        JanInfo1    = MAX(CASE WHEN t.[Month] = 1 THEN Info1 END),
        JanInfo2    = MAX(CASE WHEN t.[Month] = 1 THEN Info2 END),
        FebInfo1    = MAX(CASE WHEN t.[Month] = 2 THEN Info1 END),
        FebInfo2    = MAX(CASE WHEN t.[Month] = 2 THEN Info2 END),
        MarInfo1    = MAX(CASE WHEN t.[Month] = 3 THEN Info1 END),
        MarInfo2    = MAX(CASE WHEN t.[Month] = 3 THEN Info2 END),
        AprInfo1    = MAX(CASE WHEN t.[Month] = 4 THEN Info1 END),
        AprInfo2    = MAX(CASE WHEN t.[Month] = 4 THEN Info2 END),
        MayInfo1    = MAX(CASE WHEN t.[Month] = 5 THEN Info1 END),
        MayInfo2    = MAX(CASE WHEN t.[Month] = 5 THEN Info2 END),
        JunInfo1    = MAX(CASE WHEN t.[Month] = 6 THEN Info1 END),
        JunInfo2    = MAX(CASE WHEN t.[Month] = 6 THEN Info2 END),
        JulInfo1    = MAX(CASE WHEN t.[Month] = 7 THEN Info1 END),
        JulInfo2    = MAX(CASE WHEN t.[Month] = 7 THEN Info2 END),
        AugInfo1    = MAX(CASE WHEN t.[Month] = 8 THEN Info1 END),
        AugInfo2    = MAX(CASE WHEN t.[Month] = 8 THEN Info2 END),
        SepInfo1    = MAX(CASE WHEN t.[Month] = 9 THEN Info1 END),
        SepInfo2    = MAX(CASE WHEN t.[Month] = 9 THEN Info2 END),
        OctInfo1    = MAX(CASE WHEN t.[Month] = 10 THEN Info1 END),
        OctInfo2    = MAX(CASE WHEN t.[Month] = 10 THEN Info2 END),
        NovInfo1    = MAX(CASE WHEN t.[Month] = 11 THEN Info1 END),
        NovInfo2    = MAX(CASE WHEN t.[Month] = 11 THEN Info2 END),
        DecInfo1    = MAX(CASE WHEN t.[Month] = 12 THEN Info1 END),
        DecInfo2    = MAX(CASE WHEN t.[Month] = 12 THEN Info2 END)
    FROM Tbl t
    GROUP BY t.ID;
    
    0 讨论(0)
提交回复
热议问题