[sql] INNER JOIN과 LEFT SEMI JOIN의 차이점

INNER JOIN과 의 차이점은 무엇입니까 LEFT SEMI JOIN?

아래 시나리오에서 두 가지 다른 결과가 나오는 이유는 무엇입니까?

INNER JOIN결과 집합 많이 큽니다. 누군가 설명 할 수 있습니까? table_1에만 나타나는 이름을 얻으려고합니다 table_2.

SELECT name
FROM table_1 a
    INNER JOIN table_2 b ON a.name=b.name

SELECT name
FROM table_1 a
    LEFT SEMI JOIN table_2 b ON (a.name=b.name)



답변

INNER JOIN두 테이블에서 열에서 데이터를 반환 할 수 있으며, 하나 이상의 일치가 양쪽에 기록 된 값을 복제 할 수 있습니다. A LEFT SEMI JOIN는 왼쪽 테이블의 열만 반환 할 수 있으며 오른쪽 테이블에 하나 이상의 일치 항목이있는 왼쪽 테이블에서 각 레코드 중 하나를 생성합니다 (일치 수에 관계없이). (표준 SQL에서) 다음과 같습니다.

SELECT name
FROM table_1 a
WHERE EXISTS(
    SELECT * FROM table_2 b WHERE (a.name=b.name))

오른쪽 열에 일치하는 행 이 여러 개있는 경우 INNER JOIN는 오른쪽 테이블의 각 일치 항목에 대해 하나의 행을 LEFT SEMI JOIN반환하는 반면 a 는 오른쪽의 일치하는 행 수에 관계없이 왼쪽 테이블의 행만 반환합니다. 이것이 결과에 다른 수의 행이 표시되는 이유입니다.

table_2에만 나타나는 table_1 내의 이름을 얻으려고합니다.

그런 다음 a LEFT SEMI JOIN는 사용할 적절한 쿼리입니다.


답변

2 개의 열 (Id, Data)과 다음 데이터 만있는 TableA 및 TableB 테이블이 2 개 있다고 가정합니다.

TableA :

+----+---------+
| Id |  Data   |
+----+---------+
|  1 | DataA11 |
|  1 | DataA12 |
|  1 | DataA13 |
|  2 | DataA21 |
|  3 | DataA31 |
+----+---------+

표 B :

+----+---------+
| Id |  Data   |
+----+---------+
|  1 | DataB11 |
|  2 | DataB21 |
|  2 | DataB22 |
|  2 | DataB23 |
|  4 | DataB41 |
+----+---------+

열에 대한 내부 조인Id 은 테이블의 열과 일치하는 레코드 만 반환합니다.

.----.---------.----.---------.
| Id |  Data   | Id |  Data   |
:----+---------+----+---------:
|  1 | DataA11 |  1 | DataB11 |
:----+---------+----+---------:
|  1 | DataA12 |  1 | DataB11 |
:----+---------+----+---------:
|  1 | DataA13 |  1 | DataB11 |
:----+---------+----+---------:
|  2 | DataA21 |  2 | DataB21 |
:----+---------+----+---------:
|  2 | DataA21 |  2 | DataB22 |
:----+---------+----+---------:
|  2 | DataA21 |  2 | DataB23 |
'----'---------'----'---------'

열의 왼쪽 조인 (또는 왼쪽 외부 조인) Id은 테이블의 열과 왼쪽 테이블의 레코드와 일치하는 레코드 (오른쪽 테이블의 Null 값 )를 반환합니다.

.----.---------.----.---------.
| Id |  Data   | Id |  Data   |
:----+---------+----+---------:
|  1 | DataA11 |  1 | DataB11 |
:----+---------+----+---------:
|  1 | DataA12 |  1 | DataB11 |
:----+---------+----+---------:
|  1 | DataA13 |  1 | DataB11 |
:----+---------+----+---------:
|  2 | DataA21 |  2 | DataB21 |
:----+---------+----+---------:
|  2 | DataA21 |  2 | DataB22 |
:----+---------+----+---------:
|  2 | DataA21 |  2 | DataB23 |
:----+---------+----+---------:
|  3 | DataA31 |    |         |
'----'---------'----'---------'

열의 오른쪽 조인 (또는 오른쪽 외부 조인) Id은 테이블의 열과 오른쪽 테이블의 레코드와 일치하는 레코드 (왼쪽 테이블의 Null 값 )를 반환합니다.

┌────┬─────────┬────┬─────────┐
│ Id │  Data   │ Id │  Data   │
├────┼─────────┼────┼─────────┤
│  1 │ DataA11 │  1 │ DataB11 │
│  1 │ DataA12 │  1 │ DataB11 │
│  1 │ DataA13 │  1 │ DataB11 │
│  2 │ DataA21 │  2 │ DataB21 │
│  2 │ DataA21 │  2 │ DataB22 │
│  2 │ DataA21 │  2 │ DataB23 │
│    │         │  4 │ DataB41 │
└────┴─────────┴────┴─────────┘

열에 대한 전체 외부 조인Id 은 테이블의 열과 왼쪽 테이블의 레코드 (오른쪽 테이블의 Null 값) 및 오른쪽 테이블의 레코드 (왼쪽 테이블의 Null 값)와 일치하는 레코드를 모두 반환합니다.

╔════╦═════════╦════╦═════════╗
║ Id ║  Data   ║ Id ║  Data   ║
╠════╬═════════╬════╬═════════╣
║  - ║         ║    ║         ║
║  1 ║ DataA11 ║  1 ║ DataB11 ║
║  1 ║ DataA12 ║  1 ║ DataB11 ║
║  1 ║ DataA13 ║  1 ║ DataB11 ║
║  2 ║ DataA21 ║  2 ║ DataB21 ║
║  2 ║ DataA21 ║  2 ║ DataB22 ║
║  2 ║ DataA21 ║  2 ║ DataB23 ║
║  3 ║ DataA31 ║    ║         ║
║    ║         ║  4 ║ DataB41 ║
╚════╩═════════╩════╩═════════╝

열의 Left Semi JoinId 은 왼쪽 테이블에서만 열 을 반환하고 왼쪽 테이블에서만 일치하는 레코드를 반환합니다.

┌────┬─────────┐
│ Id │  Data   │
├────┼─────────┤
│  1 │ DataA11 │
│  1 │ DataA12 │
│  1 │ DataA13 │
│  2 │ DataA21 │
└────┴─────────┘


답변

Hive에서 시도하고 아래 출력을 얻었습니다.

1 번 테이블

1, wqe, 첸나이, 인도

2, stu, salem, 인도

3, 미아, 방갈로르, 인도

4, yepie, newyork, 미국

표 2

1, wqe, 첸나이, 인도

2, stu, salem, 인도

3, 미아, 방갈로르, 인도

5, chapie, 로스 엔젤스, 미국

내부 조인

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

1 wqe 첸나이 인도 1 wqe 첸나이 인도

2 스투 살렘 인도 2 스투 살렘 인도

3 미아 방갈로르 인도 3 미아 방갈로르 인도

왼쪽 조인

SELECT * FROM table1 LEFT JOIN table2 ON (table1.id = table2.id);

1 wqe 첸나이 인도 1 wqe 첸나이 인도

2 스투 살렘 인도 2 스투 살렘 인도

3 미아 방갈로르 인도 3 미아 방갈로르 인도

4 yepie newyork USA NULL NULL NULL NULL

왼쪽 세미 조인

SELECT * FROM table1 LEFT SEMI JOIN table2 ON (table1.id = table2.id);

1 Wqe 첸나이 인도

2 스투 살렘 인도

3 미아 방갈로르 인도

참고 : 왼쪽 테이블의 레코드 만 표시되는 반면 왼쪽 조인의 경우 두 테이블 레코드가 모두 표시됩니다.


답변