GROUP BY のイメージ
ただ並べ替えるだけの「GROUP BY」じゃなくて、指定されたカラムで分けて、分けられたそれぞれで考える というイメージ。
mysql> select * from users; +----+------+------+------+ | id | name | age | sex | +----+------+------+------+ | 1 | hoge | 12 | 1 | | 2 | foo | 76 | 0 | | 3 | bar | 45 | 0 | | 4 | hoge | 34 | 0 | | 5 | foo | 44 | 1 | | 6 | bar | 24 | 1 | +----+------+------+------+
これを以下のような name, man_age, woman_age カラムのような男女別の年齢を出すことを考える。
+------+---------+-----------+ | name | man_age | woman_age | +------+---------+-----------+ | bar | 24 | 45 | | foo | 44 | 76 | | hoge | 12 | 34 | +------+---------+-----------+
出してみる
まずは、hoge, foo, bar それぞれでまとめたいので、GROUP BY name として分ける。
mysql> select name from users; +------+ | name | +------+ | hoge | | foo | | bar | | hoge | | foo | | bar | +------+ 6 rows in set (0.00 sec) mysql> select name from users group by name; +------+ | name | +------+ | bar | | foo | | hoge | +------+ 3 rows in set (0.00 sec)
また、CASE を使うことで if else のような操作ができる。
mysql> select name,case when sex = 1 then age else 0 end as man_age, case when sex = 0 then age else 0 end as woman_age from users; +------+---------+-----------+ | name | man_age | woman_age | +------+---------+-----------+ | hoge | 12 | 0 | | foo | 0 | 76 | | bar | 0 | 45 | | hoge | 0 | 34 | | foo | 44 | 0 | | bar | 24 | 0 | +------+---------+-----------+ 6 rows in set (0.00 sec)
上記の表を name ごとにそれぞれ合計すれば出したい表ができる。
mysql> select name,sum(case when sex = 1 then age else 0 end) as man_age, sum(case when sex = 0 then age else 0 end) as woman_age from users group by name; +------+---------+-----------+ | name | man_age | woman_age | +------+---------+-----------+ | bar | 24 | 45 | | foo | 44 | 76 | | hoge | 12 | 34 | +------+---------+-----------+ 3 rows in set (0.00 sec)
まとめ
GROUP BY name ときたら、「name で分けてそれぞれで考える」 かつ並べ替えるというイメージ