sql >> データベース >  >> RDS >> Sqlserver

集計なしで行と列を転置する

    PIVOTを適用する場合 関数の場合、結果を取得するには集計関数を使用する必要がありますが、row_number()などのウィンドウ関数も使用する必要があります。 アカウント内の連絡先ごとに一意のシーケンスを生成します。

    まず、次のようにデータをクエリします:

    select account, contact,
      'contact'
        + cast(row_number() over(partition by account
                                  order by contact) as varchar(10)) seq
    from yourtable
    

    SQL FiddlewithDemoを参照してください。これにより、一意のシーケンスを持つ新しい列が作成されます:

    | ACCOUNT |   CONTACT |      SEQ |
    |---------|-----------|----------|
    |       1 | 324324324 | contact1 |
    |       1 | 674323234 | contact2 |
    

    列の数が限られている場合は、クエリをハードコーディングできます:

    select account,
      contact1, contact2, contact3, contact4
    from 
    (
      select account, contact,
        'contact'
          + cast(row_number() over(partition by account
                                    order by contact) as varchar(10)) seq
      from yourtable
    ) d
    pivot
    (
      max(contact)
      for seq in (contact1, contact2, contact3, contact4)
    ) piv;
    

    SQL Fiddle with Demo

    を参照してください

    列の数が不明な場合は、動的SQLを使用する必要があります:

    DECLARE @cols AS NVARCHAR(MAX),
        @query  AS NVARCHAR(MAX)
    
    select @cols = STUFF((SELECT ',' + QUOTENAME(seq) 
                        from
                        (
                          select 'contact'
                                  + cast(row_number() over(partition by account
                                                            order by contact) as varchar(10)) seq
                          from yourtable
                        ) d
                        group by seq
                        order by seq
                FOR XML PATH(''), TYPE
                ).value('.', 'NVARCHAR(MAX)') 
            ,1,1,'')
    
    set @query = 'SELECT account, ' + @cols + ' 
                from 
                (
                    select account, contact,
                      ''contact''
                        + cast(row_number() over(partition by account
                                                  order by contact) as varchar(10)) seq
                    from yourtable
                ) x
                pivot 
                (
                    max(contact)
                    for seq in (' + @cols + ')
                ) p '
    
    execute sp_executesql @query;
    

    SQL FiddlewithDemoを参照してください。どちらも次の結果になります:

    | ACCOUNT |  CONTACT1 |  CONTACT2 |  CONTACT3 |  CONTACT4 |
    |---------|-----------|-----------|-----------|-----------|
    |       1 | 324324324 | 674323234 |    (null) |    (null) |
    |       2 | 433243443 | 833343432 |    (null) |    (null) |
    |       3 | 787655455 |    (null) |    (null) |    (null) |
    |       4 | 455435435 | 754327545 |    (null) |    (null) |
    |       5 | 432432432 | 432433242 | 432455553 | 543544355 |
    


    1. モジュールの依存関係の使用、パート2

    2. MySQL-1つのクエリで異なる値を持つ複数の行を更新します

    3. MySQLはステータスを表示します-アクティブまたは合計接続?

    4. SQLテーブルでSQLDELETEステートメントを使用するための最良の方法