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

クロス集計転置クエリリクエスト

    特別な問題は、データがクロス集計の準備ができていないことです。 row_nameの形式のデータが必要です 、カテゴリUNIONでそれを得ることができます クエリ:

    SELECT 'metric1' AS metric, country_code, metric1 FROM tbl1
    UNION ALL
    SELECT 'metric2' AS metric, country_code, metric2 FROM tbl1
    UNION ALL
    SELECT 'metric3' AS metric, country_code, metric3 FROM tbl1
    ORDER  BY 1, 2 DESC;
    

    しかし、賢いLATERAL クエリは1回のテーブルスキャンのみを必要とし、より高速になります:

    SELECT x.metric, t.country_code, x.val
    FROM   tbl1 t
         , LATERAL (VALUES
             ('metric1', metric1)
           , ('metric2', metric2)
           , ('metric3', metric3)
           ) x(metric, val)
    ORDER  BY 1, 2 DESC;
    

    関連:

    crosstab()の単純な形式を使用する このクエリを入力として1つのパラメータを使用:

    SELECT * FROM crosstab(
     $$SELECT x.metric, t.country_code, x.val
       FROM   tbl1 t
            , LATERAL (VALUES
                ('metric1', metric1)
              , ('metric2', metric2)
              , ('metric3', metric3)
              ) x(metric, val)
       ORDER  BY 1, 2 DESC$$
       )
    AS ct (metric text, us int, uk int, fr int);
    

    国名をアルファベットの降順でリストします(デモのように)。これは、すべてのメトリックがNOT NULLで定義されていることも前提としています。 。

    一方または両方が当てはまらない場合は、代わりに2パラメータ形式を使用してください。

    「ロールアップ」を追加

    つまりメトリックごとの合計:

    SELECT * FROM crosstab(
     $$SELECT x.metric, t.country_code, x.val
       FROM  (
          TABLE tbl1
          UNION ALL
          SELECT 'zzz_total', sum(metric1)::int, sum(metric2)::int, sum(metric3)::int  -- etc.
          FROM tbl1
          ) t
            , LATERAL (VALUES
                ('metric1', metric1)
              , ('metric2', metric2)
              , ('metric3', metric3)
              ) x(metric, val)
       ORDER  BY 1, 2 DESC$$
       )
    AS ct (metric text, total int, us int, uk int, fr int);

    'zzz_total' は任意のラベルであり、最後にアルファベット順に並べ替える必要があります(または、crosstab()の2パラメーター形式が必要です 。

    たくさんある場合 メトリック列の場合、クエリ文字列を動的に作成することをお勧めします。関連:

    また、次のPostgres 9.5(現在はベータ版)では、専用の ROLLUPのSQL句
    関連:




    1. SQLServerへのUTF-16/Unicodeデータの保存

    2. 問題を引き起こすphpdb変数の下線

    3. クエリ結果をMariaDBのコンマ区切りリストに変換する

    4. PL / SQLで文字列を分割する方法は?