LEFT JOIN / RIGHT JOIN
| 対応: | SQL-92(1992) |
|---|
片方のテーブルの全行を保持しながら結合する方法です。一致しない行にはNULLが入ります。
構文
『LEFT JOIN』:左テーブル(FROM側)の全行を保持して結合します。
SELECT 列名 FROM テーブル1 LEFT JOIN テーブル2 ON テーブル1.結合列 = テーブル2.結合列;
『LEFT OUTER JOIN』は『LEFT JOIN』と同じ意味です(『OUTER』は省略可)。
SELECT 列名 FROM テーブル1 LEFT OUTER JOIN テーブル2 ON テーブル1.結合列 = テーブル2.結合列;
『RIGHT JOIN』:右テーブル(JOIN側)の全行を保持して結合します。
SELECT 列名 FROM テーブル1 RIGHT JOIN テーブル2 ON テーブル1.結合列 = テーブル2.結合列;
INNER JOIN との違い
| 結合種別 | 動作 |
|---|---|
| INNER JOIN | 両テーブルに一致する行のみを取得します。どちらかに存在しない行は結果に含まれません。 |
| LEFT JOIN | 左テーブル(FROM側)の全行を必ず含みます。右テーブルに一致しない場合、右テーブルの列はNULLになります。 |
| RIGHT JOIN | 右テーブル(JOIN側)の全行を必ず含みます。左テーブルに一致しない場合、左テーブルの列はNULLになります。 |
サンプルコード
以下の『employees』テーブルと『departments』テーブルを例に説明します。
全社員を取得します。部署未設定の社員も含みます(department列はNULLになります)。
sample_left_right_join.sql
SELECT e.name, d.department_name FROM employees AS e LEFT JOIN departments AS d ON e.department_id = d.id;
+---------+-----------------------------+ | name | department_name | +---------+-----------------------------+ | 孫悟空 | 亀仙流 | | ベジータ | カプセルコーポレーション | | ブルマ | NULL | +---------+-----------------------------+ 3 rows in set
部署未設定の社員を取得します(departments側がNULLの行を絞り込みます)。
sample_left_right_join.sql
SELECT e.name, e.department_id FROM employees AS e LEFT JOIN departments AS d ON e.department_id = d.id WHERE d.id IS NULL;
+--------+---------------+ | name | department_id | +--------+---------------+ | ブルマ | NULL | +--------+---------------+ 1 row in set
全部署を取得します。社員がいない部署も含みます(ナメック星人居住区の name 列は NULL になります)。
sample_left_right_join.sql
SELECT d.department_name, e.name FROM departments AS d LEFT JOIN employees AS e ON d.id = e.department_id;
+-----------------------------+---------+ | department_name | name | +-----------------------------+---------+ | 亀仙流 | 孫悟空 | | カプセルコーポレーション | ベジータ | | ナメック星人居住区 | NULL | +-----------------------------+---------+ 3 rows in set
『RIGHT JOIN』で全部署を取得します(LEFT JOIN の左右を入れ替えた例)。
sample_left_right_join.sql
SELECT d.department_name, e.name FROM employees AS e RIGHT JOIN departments AS d ON e.department_id = d.id;
+-----------------------------+---------+ | department_name | name | +-----------------------------+---------+ | 亀仙流 | 孫悟空 | | カプセルコーポレーション | ベジータ | | ナメック星人居住区 | NULL | +-----------------------------+---------+ 3 rows in set
データベース別の書き方
『LEFT JOIN』・『RIGHT JOIN』の構文は主要なデータベースで共通して使用できます。
-- MySQL・PostgreSQL・SQLite 共通 SELECT e.name, d.department_name FROM employees AS e LEFT JOIN departments AS d ON e.department_id = d.id;
SQLite は『LEFT JOIN』をサポートしていますが、『RIGHT JOIN』には対応していません(3.39.0 以降で対応)。古いバージョンの SQLite では『LEFT JOIN』でテーブルの順序を入れ替えることで代替できます。
概要
『LEFT JOIN』は実務で非常によく使われる結合です。「すべての○○を取得し、関連する△△があれば一緒に表示する」という要件に適しています。
一致しない行を検出する(存在しない行を探す)パターンでも『LEFT JOIN』が使われます。結合後に『WHERE 右テーブル.id IS NULL』で絞り込むことで、左テーブルにのみ存在する行(孤立レコード)を見つけることができます。
『RIGHT JOIN』は『LEFT JOIN』でテーブルの順番を入れ替えた場合と同じ結果が得られます。そのため実務では読みやすさの観点から『LEFT JOIN』に統一することが多いです。両テーブルの全行を保持したい場合は『FULL OUTER JOIN』を参照してください。
記事の間違いや著作権の侵害等ございましたらお手数ですがこちらまでご連絡頂ければ幸いです。