SQL 将行转为列

SQL Pivot Rows to Column

以为这很容易,但我遇到了麻烦。我需要旋转(或反旋转)一个包含 100,000 多行的 table(称为 da_LMP_downloads)。我从这个开始:table_before

之前:

集市日 |节点| Node_Type | LMP_Value| HE1 | HE2| HE 3|.......|HE24|

2012 年 10 月 1 日 |AEC|界面 | LMP | 17.82 | 16.44 | 16.45

2012 年 10 月 1 日 |AEC|界面 |中冶 | .14 | .16 | .62

2012 年 10 月 1 日 |AEC|界面 |多层板 | -.38 | -.34 | .34

但需要它在枢轴后看起来像这样:table_after

之后:

Market_Day |节点 |贺 |达林普 | daMCC | daMLC

2012 年 10 月 1 日 |工程建设委员会 | 1 | 17.82 | .14 | -.38

2012 年 10 月 1 日 |工程建设委员会 | 2| 16.44| .16 | -.34

2012 年 10 月 1 日 |工程建设委员会 | 3 | 16.45 | .62 | .34

如果您的 dbms 是 SQL 服务器,那么您可以使用 CROSS APPLY 和 VALUES 来实现 "unpivot" 部分,但是您还需要一个小的 "pivot" 操作为此, GROUP BY 将起作用。请注意,这仅适用于 SQL 服务器,其他数据库对 unpivot/pivot.

的语法有很大不同
/* input looks like this...
Market_Day Node Node_Type LMP_Value HE1   HE2   .... HE24
2012-10-01 AEC Interface  LMP       17.82 16.44 .... 19.77
*/
SELECT
      sq.Market_Day
    , sq.Node
    , sq.Node_Type
    , sq.HE
    , MAX(sq.daLMP) AS daLMP
    , MAX(sq.daMCC) AS daMCC
    , MAX(sq.daMLC) AS daMLC
FROM (
      SELECT
            t.Market_Day
          , t.Node
          , t.Node_Type
          , ca.HE
          , CASE WHEN LMP_Value = 'LMP' THEN ca.val END AS daLMP
          , CASE WHEN LMP_Value = 'MCC' THEN ca.val END AS daMCC
          , CASE WHEN LMP_Value = 'MLC' THEN ca.val END AS daMLC
      FROM Table1 t
            CROSS APPLY (
                  VALUES
                        (1, HE1)
                      , (2, HE2)
                      , (3, HE3)
                      , (4, HE4)
                      , (5, HE5)
                      , (6, HE6)
                      , (7, HE7)
                      , (8, HE8)
                      , (9, HE9)
                      , (10, HE10)
                      , (11, HE11)
                      , (12, HE12)
                      , (13, HE13)
                      , (14, HE14)
                      , (15, HE15)
                      , (16, HE16)
                      , (17, HE17)
                      , (18, HE18)
                      , (19, HE19)
                      , (20, HE20)
                      , (21, HE21)
                      , (22, HE22)
                      , (23, HE23)
                      , (24, HE24)
                        ) AS ca (HE, val)
    ) AS sq
GROUP BY
      sq.Market_Day
    , sq.Node
    , sq.Node_Type
    , sq.HE

注意 TSQL 实际上确实同时具有 "pivot" 和 "unpivot" 运算符,但我发现使用交叉 apply/values 既高效又易于实现。