結合の理解が壊れています。 これは間違いなく円の交差点ではありません

そのため、私はWebプログラマーの地位についてかなりの数のインタビューを行いました。 私が尋ねる必須の質問の1つは、INNER JOINとLEFT JOINの違いです。


最も一般的な答えは次のようなものです。「内部結合はセットの共通部分に似ています。つまり、両方のテーブルに残っているものだけが残ります。他のすべての行はnull "が追加されます。 また、交差する円を描くこともあります。


セットとサークルの交差点でのこれらの答えにうんざりしていたので、人々を修正することさえ止めました。


事実は、この答えが一般的に間違っているということです。 まあ、または少なくとも正確ではありません。


その理由を見てみましょう。同時に、いくつかの微妙な結合に触れてみましょう。


まず、テーブルは多数ではありません。 数学的な定義では、セット内のすべての要素は一意であり、繰り返されません。一般的な場合のテーブルでは、実際にはそうではありません。 2番目の問題は、「交差点」という用語が混乱するだけであることです。


更新 。コメントでは、集合論と一意性についての激しい議論があります。非常に興味深い、私は多くの新しいことを学びました、ありがとう)


インナージョイン


すぐに例を挙げましょう。


したがって、1つのid列を持つ2つの同一のテーブルを作成しましょう。これらの各テーブルには、1の値と2つの値を持つ2つの行があります。


INSERT INTO table1
(id)
VALUES
(1),
(1)
(3);

INSERT INTO table2
(id)
VALUES
(1),
(1),
(2);

, , ,


SELECT *
FROM table1
   INNER JOIN table2
      ON table1.id = table2.id;

" ", " ", .



:


| id  | id  |
| --- | --- |
| 1   | 1   |
| 1   | 1   |
| 1   | 1   |
| 1   | 1   |


??


, CROSS JOIN. - .


CROSS JOIN — . , , 3 , — 2:


select * from t1;

 id 
----
  1
  2
  3

select * from t2;

 id 
----
  4
  5

CROSS JOIN 6 .


select * 
from t1
   cross join t2; 

 id | id 
----+----
  1 |  4
  1 |  5
  2 |  4
  2 |  5
  3 |  4
  3 |  5

, .


t1 INNER JOIN t2 ON condition

— , ,


t1 CROSS JOIN t2  WHERE condition

.. INNER JOINcondition. -, , , - .


disclaimer: inner join cross join , , , : . .


LEFT JOIN


, , null, , .


, :


insert into t1 
(id)
values
(1),
(1),
(3);

insert into t2
(id)
values
(1),
(1),
(4),
(5);

LEFT JOIN:


SELECT * 
FROM t1
   LEFT JOIN t2 
       ON t1.id = t2.id;

5 , , .


| id  | id  |
| --- | --- |
| 1   | 1   |
| 1   | 1   |
| 1   | 1   |
| 1   | 1   |
| 3   |     |

, LEFT JOIN — INNER JOIN (.. , - ), , .


LEFT JOIN :


SELECT * 
FROM t1 
   CROSS JOIN t2
   WHERE t1.id = t2.id

UNION ALL

SELECT t1.id, null
   FROM t1
   WHERE NOT EXISTS (
        SELECT
        FROM t2
        WHERE t2.id = t1.id
   )

, , , ..


ON


, 99% , ON id id . .


, users_stats, ip .


SELECT s.id, c.city 
FROM users_stats AS s
    JOIN cities_ip_ranges AS c
        ON c.ip_range && s.ip

&& — (. ip4r)


ON true, CROSS JOIN


"table1 JOIN table2 ON true"  == "table1 CROSS JOIN table2"


, join- . " ". , join- . .. - - php.


, , .


, , . , . , , , .


O(n!), n — . , , , . CTE; , , , , , .


, . , , 'LEFT JOIN… WHERE… IS NULL', EXISTS. , .



, . , , "".


, , , . — , , . " ". .


Update. : https://habr.com/ru/post/450528/



Source: https://habr.com/ru/post/J448072/


All Articles