ROLLUPを使って合計行を作ってみる【PostgreSQL】

2020年12月30日PostgreSQLその他

合計行を作る方法

合計行を作る方法は、ROLLUPを使います。

ここではその使い方と、表示結果を調整する方法を、実例で紹介します。

 

ROLLUPの構文

ROLLUPの構文は以下の形になります。

簡単にいうと、GROUP BYの時の構文「GROUP BY 列名』を

『GROUP BY ROLLUP(列名)』に変えるだけです。

--合計行を一緒に取得するSELECT文
select 列名1 , sum(列名2)
From テーブル名
group by ROLLUP(列名1);

--複数列でGROUP BYする時
select 列名1 , 列名2 , sum(列名3)
From テーブル名
group by ROLLUP(列名1 , 列名2);

 

実例で見てみます。こんなデータを用意しました(参考程度に)。

イメージは、学生と教科ごとの点数のデータです。

 

用意したテーブルはこんな感じ。

CREATE TABLE test_score
(
    student_code character varying(10) NOT NULL,  -- 学生コード
    student_name character varying(50) ,          -- 学生名
    subject_code character varying(10) NOT NULL,  -- 教科コード
    subject_name character varying(50) ,          -- 教科名
    score integer,                                -- 点数
    CONSTRAINT pk_test_score PRIMARY KEY (student_code, subject_code)
)

 

合計行を含めて取得するSQLはこうなります。

select 
	student_code               -- 学生コード
  , max(student_name)          -- 学生名
  , sum(score)                 -- 合計点
from test_score 
group by rollup(student_code)  -- rollupで合計行をだす
order by student_code;

 

結果の画像です。

合計行が4行目に表示されたのがわかります。

 

上の例では少し見た目が悪いのでこのようにSQLを変えてみます。

具体的には①合計行は学生コードがnullになっているので、わかりやすく「合計」と表示、

②学生名はmaxで取得している加減があり名前が表示されているので、nullにします。

select 
  --1列目:学生コードがnullなら「合計」と表示、それ以外ならそのまま表示
  case when student_code is null then '合計' 
  else student_code end as student_code

  --2列目:学生名は合計行ならnullにする
  , case when student_code is null then null 
    else max(student_name) end as student_name

  --3列名:合計行
  , sum(score) 
from test_score group by rollup(student_code) 
order by student_code;

 

結果の画像です。

合計と表示され、名前がnullになりうまくいきました。