SQL 結合(JOIN)


SQL JOIN は、2つ以上のテーブルの行を結合するために使用されます。

下図は、LEFT JOIN、RIGHT JOIN、INNER JOIN、OUTER JOIN に関連する7つの使い方を示しています。

種類説明
INNER JOIN2つのテーブルで結合条件を満たすレコードを返します(交差)。
LEFT JOIN右テーブルに一致するレコードがない場合でも、左テーブルのすべてのレコードを返します(左テーブルを保持)。
RIGHT JOIN左テーブルに一致するレコードがない場合でも、右テーブルのすべてのレコードを返します(右テーブルを保持)。
FULL OUTER JOIN2つのテーブルの和集合を返し、一致するレコードと一致しないレコードの両方を含みます。
CROSS JOIN2つのテーブルのデカルト積を返し、左テーブルの各レコードと右テーブルの各レコードを組み合わせます。
SELF JOINテーブルをそれ自身と結合します。
NATURAL JOIN同名のフィールドに基づいて自動的にマッチングして結合するテーブル。

サンプルデータ

表1:Customers

CustomerID Name
1 Alice
2 Bob
3 Charlie

表2:Orders

OrderID CustomerID Product
101 1 Laptop
102 2 Phone
103 4 Tablet

各結合結果の比較

JOIN の種類 結果
INNER JOIN 2つのテーブルで一致するレコードを返します。この例では、CustomerID が 1 と 2 のレコードのみが両方のテーブルで一致するため、これらのレコードだけが返されます。
LEFT JOIN 右テーブル(Orders)に一致するレコードがない場合でも、左テーブル(Customers)のすべてのレコードを返します。左テーブルで一致しない右テーブルのレコードについては、結果の右テーブルのフィールドは NULL になります。この例では、CustomerID が 3 のレコードは右テーブルに一致しないため、対応する Product は NULL になります。
RIGHT JOIN 左テーブル(Customers)に一致するレコードがない場合でも、右テーブル(Orders)のすべてのレコードを返します。右テーブルで一致しない左テーブルのレコードについては、結果の左テーブルのフィールドは NULL になります。この例では、OrderID が 103 のレコードは左テーブルに一致しないため、対応する Name は NULL になります。
FULL OUTER JOIN 一致するかどうかに関係なく、2つのテーブルのすべてのレコードを返します。どちらかのテーブルに一致するレコードがない場合、そのテーブルのフィールドは NULL になります。この例では、CustomerID が 3 のレコードと OrderID が 103 のレコードは、それぞれ相手のテーブルでは NULL として表示されます。
CROSS JOIN 2つのテーブルのデカルト積を返します。つまり、左テーブルの各行と右テーブルの各行を組み合わせます。この例では、各顧客が各注文と組み合わされ、複数の結果が生成されます。
SELF JOIN テーブルをそれ自身と結合します。これは通常、従業員とそのマネージャーの関係など、テーブル内の相互に関連するレコードを照会するために使用されます。

SQL JOIN

SQL JOIN 句は、テーブル間の共通フィールドに基づいて、2つ以上のテーブルの行を結合するために使用されます。

最も一般的な JOIN の種類:SQL INNER JOIN(シンプルな JOIN)。 SQL INNER JOIN は、JOIN 条件を満たすすべての行を複数のテーブルから返します。

構文:

SELECT column1, column2, ...
FROM table1
JOIN table2 ON condition;

パラメータの説明:

  • column1, column2, ...:選択するフィールド名。複数のフィールドを指定できます。フィールド名を指定しない場合は、すべてのフィールドが選択されます。
  • table1:結合する最初のテーブル。
  • table2:結合する2番目のテーブル。
  • condition:結合条件。結合方法を指定します。

デモデータベース

このチュートリアルでは、サンプル サンプルデータベースを使用します。

以下は "Websites" テーブルから選択したデータです:

+----+--------------+---------------------------+-------+---------+
| id | name         | url                       | alexa | country |
+----+--------------+---------------------------+-------+---------+
| 1  | Google       | https://www.google.cm/    | 1     | USA     |
| 2  | 淘宝          | https://www.taobao.com/   | 13    | CN      |
| 3  | サンプル      | http://www.example.com/    | 4689  | CN      |
| 4  | 微博          | http://weibo.com/         | 20    | CN      |
| 5  | Facebook     | https://www.facebook.com/ | 3     | USA     |
| 7  | stackoverflow | http://stackoverflow.com/ |   0 | IND     |
+----+---------------+---------------------------+-------+---------+

以下は "access_log" ウェブサイトアクセス記録テーブルのデータです:

mysql> SELECT * FROM access_log;
+-----+---------+-------+------------+
| aid | site_id | count | date       |
+-----+---------+-------+------------+
|   1 |       1 |    45 | 2016-05-10 |
|   2 |       3 |   100 | 2016-05-13 |
|   3 |       1 |   230 | 2016-05-14 |
|   4 |       2 |    10 | 2016-05-14 |
|   5 |       5 |   205 | 2016-05-14 |
|   6 |       4 |    13 | 2016-05-15 |
|   7 |       3 |   220 | 2016-05-15 |
|   8 |       5 |   545 | 2016-05-16 |
|   9 |       3 |   201 | 2016-05-17 |
+-----+---------+-------+------------+
9 rows in set (0.00 sec)

注意してください、"Websites" テーブルの "id" 列は "access_log" テーブルのフィールド "site_id"。上記の2つのテーブルは "site_id" 列によって関連付けられています。

次に、以下の SQL ステートメント(INNER JOIN を含む)を実行すると:

例

SELECT Websites.id, Websites.name, access_log.count, access_log.date
FROM Websites
INNER JOIN access_log
ON Websites.id=access_log.site_id;

上記の SQL を実行すると、出力結果は次のとおりです:



さまざまな SQL JOIN

例の説明を続ける前に、使用できるさまざまな SQL JOIN の種類を一覧にします:

  • INNER JOIN:テーブルに少なくとも1つの一致がある場合に行を返します
  • LEFT JOIN:右テーブルに一致がなくても、左テーブルからすべての行を返します
  • RIGHT JOIN:左テーブルに一致がなくても、右テーブルからすべての行を返します
  • FULL JOIN:どちらかのテーブルに一致が存在する限り、行を返します
その他の拡張