SELF JOIN
SELECT
*
FROM ECOLI_DATA ED
LEFT JOIN ECOLI_DATA ED2 ON ED.PARENT_ID = ED2.ID;
SELF JOIN에 대한 이해가 잘 안되서 여러가지 공부를 했습니다.
보통 부모-자식, 상사-부하 같은 관계를 찾을때 쓰입니다.
먼저 테이블을 보시죠. 데이터는 프로그래머스 < 대장균들의 자식의 수 구하기> 문제에서 가져왔습니다.
ID | PARENT_ID | SIZE_OF_COLONY | DIFFERENTIATION_DATE | GENOTYPE |
1 | NULL | 10 | 2019-01-01 | 5 |
2 | NULL | 2 | 2019-01-01 | 3 |
3 | 1 | 100 | 2020-01-01 | 4 |
4 | 2 | 17 | 2020-01-01 | 4 |
5 | 2 | 10 | 2020-01-01 | 6 |
6 | 4 | 101 | 2021-01-01 | 22 |
문제는 대장균들의 자식수를 구하기 인데 이때 SELF JOIN을 하면 됩니다.
해깔릴 수 있기 때문에 비유를 들어서 설명 해 보겠습니다.
각 가족 구성원은 고유한 번호(ID)가 적힌 신분증을 가지고 있습니다. 만약 그 사람이 부모에게서 태어났다면, 그 신분증에는 부모의 번호(PARENT_ID)도 함께 기록되어 있죠. 이 설정을 바탕으로 SQL SELFJOIN을 이해 할 수 있습니다.
SELECT
*
FROM ECOLI_DATA ED
LEFT JOIN ECOLI_DATA PARENT ON ED.PARENT_ID = PARENT.ID;
<결과>
ID | PARENT_ID | SIZE_OF_COLONY | DIFFERENTIATION_DATE | GENOTYPE | ID | PARENT_ID | SIZE_OF_COLONY | DIFFERENTIATION_DATE | GENOTYPE |
1 | null | 10 | 2019-01-01 | 5 | null | null | null | null | null |
2 | null | 2 | 2019-01-01 | 3 | null | null | null | null | null |
3 | 1 | 100 | 2020-01-01 | 4 | 1 | null | 10 | 2019-01-01 | 5 |
4 | 2 | 17 | 2020-01-01 | 4 | 2 | null | 2 | 2019-01-01 | 3 |
5 | 2 | 10 | 2020-01-01 | 6 | 2 | null | 2 | 2019-01-01 | 3 |
6 | 4 | 101 | 2021-01-01 | 22 | 4 | 2 | 17 | 2020-01-01 | 4 |
이 쿼리는 각 사람의 신분증을 보면서,
"내 신분증에 적힌 부모 번호(PARENT_ID)가 누구의 신분증 번호(ID)와 일치하는지 찾아봐!"
라고 말하는 것과 같습니다.
즉, "내가 누구의 자식인가?"라는 질문에 답하는 것입니다.
예를 들어, 만약 B의 신분증에 부모 번호가 1로 기록되어 있다면, 신분증 번호가 1인 사람(A)을 찾아서 B의 부모 정보를 연결하는 것입니다.
그렇다면 내 자식은 어떻게 찾을까요?
SELECT
*
FROM ECOLI_DATA ED
LEFT JOIN ECOLI_DATA ED2 ON ED.ID = ED2.PARENT_ID;
ID | PARENT_ID | SIZE_OF_COLONY | DIFFERENTIATION_DATE | GENOTYPE | ID | PARENT_ID | SIZE_OF_COLONY | DIFFERENTIATION_DATE | GENOTYPE |
1 | null | 10 | 2019-01-01 | 5 | 3 | 1 | 100 | 2020-01-01 | 4 |
2 | null | 2 | 2019-01-01 | 3 | 5 | 2 | 10 | 2020-01-01 | 6 |
2 | null | 2 | 2019-01-01 | 3 | 4 | 2 | 17 | 2020-01-01 | 4 |
3 | 1 | 100 | 2020-01-01 | 4 | null | null | null | null | null |
4 | 2 | 17 | 2020-01-01 | 4 | 6 | 4 | 101 | 2021-01-01 | 22 |
5 | 2 | 10 | 2020-01-01 | 6 | null | null | null | null | null |
6 | 4 | 101 | 2021-01-01 | 22 | null | null | null | null | null |
이 쿼리는 반대로,
"내 신분증 번호(ID)가 다른 사람들의 부모 번호(PARENT_ID)로 쓰여 있는지 찾아봐!"
라고 말하는 것과 같습니다.
즉, "내가 누구의 부모인가?"라는 질문에 답하는 것입니다.
예를 들어, 만약 A의 신분증 번호가 1이라면, 부모 번호가 1로 기록된 다른 사람들(B, C 등)을 찾아서 A의 자식 정보를 연결합니다.
정리
- 부모 조회 쿼리 (ED.PARENT_ID = ED2.ID):
"내 신분증에 적힌 부모 번호를 통해 내 부모의 신분증을 찾아라."
→ 내가 누구의 자식인지 알아보는 쿼리 - 자식 조회 쿼리 (ED.ID = ED2.PARENT_ID):
"내 신분증 번호를 다른 사람들의 부모 번호와 비교해서, 내 번호를 부모로 기록한 사람들을 찾아라."
→ 내가 누구의 부모인지 알아보는 쿼리
이처럼, 조인 조건에 따라 내가 누구의 자식인지 혹은 누구의 부모인지를 확인할 수 있습니다.
데이터 관계를 파악할 때 원하는 관점(부모 정보 vs. 자식 정보)에 따라 적절한 조건을 선택하면 됩니다.