논리적 조인 포스트:
2025.02.13 - [자격증/SQLD] - [SQLD] 3-3: 논리적 JOIN (조인)의 모든 것
[SQLD] 3-3: 논리적 JOIN (조인)의 모든 것
이전 포스트:2025.02.13 - [자격증/SQLD] - [SQLD] Chapter 3-2 GROUP BY & HAVING & ORDER [SQLD] Chapter 3-2 GROUP BY & HAVING & ORDER1. GROUP BY 개념GROUP BY 절은 데이터를 특정 기준에 따라 그룹화하여 집계 연산을 수행할 때
rnasterofmysea.tistory.com
🔹 논리적 조인 vs. 물리적 조인
SQL에서 조인은 크게 두 가지 관점에서 분류할 수 있습니다.
구분 | 설명 | 종류 |
논리적 조인 (Logical Join) | 데이터가 어떻게 결합되는지를 정의 | INNER JOIN, OUTER JOIN (LEFT, RIGHT, FULL), CROSS JOIN, SELF JOIN |
물리적 조인 (Physical Join) | SQL 엔진이 실제로 조인을 수행하는 방법 | Nested Loop Join, Sort Merge Join, Hash Join |
즉, 논리적 조인은 데이터베이스 사용자가 SQL을 작성할 때 사용하는 개념,
반면 물리적 조인은 SQL 엔진이 내부적으로 SQL을 실행할 때 선택하는 방식입니다.

[SQLD SP02] 물리적 조인(JOIN)의 모든 것
🔹 해시 조인(Hash Join)이란?
해시 조인은 데이터베이스에서 대량의 데이터를 조인할 때 효과적인 기법으로, 해시 함수(Hash Function)를 사용하여 조인을 수행하는 방식입니다.
특히 조인 칼럼에 인덱스가 없는 경우에도 효과적으로 사용할 수 있는 조인 방법입니다.
🔸 Hash Join의 동작 원리
Hash Join은 두 개의 입력 테이블에서 조인 연산을 수행하는 방식으로, **두 단계(Build 단계, Probe 단계)**로 진행됩니다.
1️⃣ Build 단계 (선행 테이블 - Build Input)
- **선행 테이블(Smaller Table)**의 조인 키 값을 기반으로 해시 테이블(Hash Table)을 생성합니다.
- 이때, **해시 함수(Hash Function)**를 사용하여 같은 값은 같은 해시 버킷(Hash Bucket)에 저장되도록 합니다.
- 해시 테이블은 메모리에 저장되며, 크기가 클 경우 일부는 디스크에 저장될 수 있습니다.
2️⃣ Probe 단계 (후행 테이블 - Probe Input)
- **후행 테이블(Larger Table)**을 순차적으로 읽으면서, Build 단계에서 만든 해시 테이블을 참조하여 조인된 데이터를 찾음.
- 후행 테이블의 조인 키 값을 해시 함수에 적용하여 해당 키가 해시 테이블에 있는지 검사하는 방식.
🔸 Hash Join의 특징
✅ 해시 조인은 인덱스가 없어도 수행 가능
- 조인 키에 인덱스가 존재하지 않아도 해시 함수를 이용하여 조인을 수행할 수 있음.
- 따라서, 대량의 데이터를 인덱스 없이도 빠르게 조인할 수 있는 장점이 있음.
✅ '=' (동등 조인)만 지원
- Hash Join은 해시 함수가 동일한 값을 동일한 해시 버킷으로 매핑하는 원리를 사용하기 때문에,
비교 연산자(=, EQUI JOIN)를 사용하는 동등 조인(Equal Join)에서만 사용 가능. - 범위 조인 (<, >, BETWEEN)에서는 사용할 수 없음.
✅ CPU 연산이 많이 발생
- 해시 테이블을 만들고 해시 함수를 적용하는 과정에서 CPU 연산 부담이 큼.
- 따라서, 작은 테이블을 선행 테이블(Build Input)로 사용하는 것이 유리.
✅ 메모리 사용량이 중요
- 해시 테이블을 메모리에 적재해야 하므로, 메모리가 충분한 경우에 효과적.
- 하지만, 해시 테이블이 **메모리를 초과하면 디스크의 임시 공간(TEMP 영역)**을 사용하게 되어 성능이 저하될 수 있음.
✅ 선행 테이블(Build Input)은 작은 테이블이 유리
- 해시 테이블을 만들 때 작은 테이블을 Build Input으로 설정하면 메모리 사용을 줄이고 성능을 향상시킬 수 있음.
- 후행 테이블(Probe Input)은 큰 테이블이더라도 조인 과정에서 빠르게 탐색 가능.
✅ 병렬처리에 유리
- 해시 함수는 여러 개의 해시 버킷으로 데이터를 나누므로, **병렬 처리(Parallel Execution)**에 유리함.
🔸 Hash Join 실행 예제
다음 SQL을 실행하면 Hash Join이 사용될 가능성이 있음.
SELECT E.EMPLOYEE_ID, E.EMPLOYEE_NAME, D.DEPARTMENT_NAME
FROM EMPLOYEES E
JOIN DEPARTMENTS D ON E.DEPARTMENT_ID = D.DEPARTMENT_ID;
- 위 쿼리는 EMPLOYEES 테이블과 DEPARTMENTS 테이블을 부서 ID (DEPARTMENT_ID) 기준으로 조인합니다.
- EMPLOYEES가 큰 테이블이고, DEPARTMENTS가 작은 테이블이라면 DEPARTMENTS가 Build Input이 되고 EMPLOYEES가 Probe Input이 됨.
🔸 Hash Join의 장점과 단점
✅ 장점
✔ 대량의 데이터를 빠르게 조인 가능
✔ 인덱스가 없어도 조인 가능
✔ 병렬 처리에 유리
❌ 단점
✖ 해시 테이블을 만들기 때문에 CPU 연산이 많이 발생
✖ 해시 테이블이 커질 경우 메모리 초과로 인해 디스크 I/O 비용 증가
✖ 동등 조인(=)에서만 사용 가능하며, 범위 조인(<, >, BETWEEN)에서는 불가능
🔹 Nested Loop Join (NL Join)
Nested Loop Join은 **하나의 테이블(외부 테이블)**을 순회하면서 **다른 테이블(내부 테이블)**을 반복적으로 조회하는 방식의 조인입니다.
일반적으로 인덱스가 있는 경우 빠르게 동작하며, 데이터 양이 적을 때 효과적입니다.
1️⃣ Nested Loop Join의 동작 원리
두 개의 테이블(외부 테이블과 내부 테이블)을 사용하여 반복문을 수행하면서 조인하는 방식입니다.
✅ 1. 외부 테이블(Outer Table) 선택
- 먼저, 외부 테이블에서 한 행을 선택합니다.
✅ 2. 내부 테이블(Inner Table)에서 매칭되는 값 찾기
- 내부 테이블에서 조인 조건을 만족하는 행을 찾음 (주로 인덱스를 활용하여 빠르게 검색).
✅ 3. 반복 수행
- 외부 테이블의 모든 행에 대해 내부 테이블을 반복 조회하면서 조인을 수행.
2️⃣ Nested Loop Join의 특징
✅ 인덱스가 있는 경우 빠름
- 내부 테이블(Inner Table)의 조인 칼럼에 인덱스가 존재하면 빠르게 검색 가능.
- 하지만, 인덱스가 없으면 성능 저하.
✅ 모든 비교 연산(=, <, >, BETWEEN)에서 사용 가능
- 비교 연산자를 자유롭게 사용할 수 있어 다양한 조인 조건을 적용 가능.
✅ 소규모 데이터에서 적합
- 데이터 양이 적거나 선행 테이블(Outer Table)의 행 수가 적을 때 유리.
- 하지만, 대량의 데이터를 조인하면 성능이 급격히 저하됨 (O(N*M) 성능).
✅ 랜덤 I/O 발생 가능
- 인덱스를 사용하지 않으면 매번 내부 테이블을 전체 검색(Full Scan) 하게 되어 성능이 크게 떨어질 수 있음.
3️⃣ Nested Loop Join 실행 예제
SELECT E.EMPLOYEE_ID, E.EMPLOYEE_NAME, D.DEPARTMENT_NAME
FROM EMPLOYEES E
JOIN DEPARTMENTS D ON E.DEPARTMENT_ID = D.DEPARTMENT_ID;
- 외부 테이블(EMPLOYEES)의 한 행을 선택한 후,
- 내부 테이블(DEPARTMENTS)의 인덱스를 사용하여 조인되는 행을 찾음.
4️⃣ Nested Loop Join의 장점과 단점
✅ 장점
✔ 인덱스를 활용하면 빠르게 수행 가능
✔ 모든 비교 연산(=, <, >, BETWEEN) 사용 가능
✔ 작은 데이터셋에서는 빠른 성능
❌ 단점
✖ 대량 데이터 조인 시 비효율적 (O(N*M) 연산)
✖ 내부 테이블에 인덱스가 없으면 Full Scan 발생 → 성능 저하
✖ 랜덤 I/O 증가로 인해 디스크 I/O가 많아질 수 있음
🔹 Sort Merge Join (SMJ)
Sort Merge Join은 두 개의 테이블을 정렬한 후, 병합하여 조인하는 방식입니다.
인덱스가 없어도 대량의 데이터 조인에서 효율적이며, 모든 비교 연산(=, <, >, BETWEEN)에서 사용 가능합니다.
1️⃣ Sort Merge Join의 동작 원리
Sort Merge Join은 **두 단계(Sort 단계, Merge 단계)**로 이루어집니다.
✅ 1. Sort 단계 (정렬)
- 조인 대상 테이블을 조인 키 기준으로 정렬합니다.
- 정렬이 완료된 후, 두 개의 테이블을 나란히 비교할 수 있는 상태가 됨.
✅ 2. Merge 단계 (병합)
- 정렬된 두 테이블을 하나씩 스캔하면서 일치하는 값들을 빠르게 매칭.
- 양쪽 테이블을 순차적으로 스캔하기 때문에 빠름.
2️⃣ Sort Merge Join의 특징
✅ 대량 데이터에서 효과적
- 인덱스가 없어도 성능이 우수하여 대량 데이터 조인에서 활용됨.
- 단, 정렬(Sort) 과정이 필요하기 때문에 데이터가 정렬되어 있지 않으면 비용 발생.
✅ 모든 비교 연산(=, <, >, BETWEEN)에서 사용 가능
- Nested Loop Join과 달리 동등 조인(=)뿐만 아니라, 범위 조인(<, >, BETWEEN)에서도 사용 가능.
✅ 순차적 접근이므로 디스크 I/O 감소
- 정렬 후 순차적으로 테이블을 읽으며 조인하므로 랜덤 I/O가 줄어듦.
✅ 정렬이 되어 있으면 빠르게 수행 가능
- 조인 대상이 이미 정렬되어 있다면 Sort 단계 없이 Merge 단계만 수행하므로 성능이 향상됨.
3️⃣ Sort Merge Join 실행 예제
SELECT E.EMPLOYEE_ID, E.EMPLOYEE_NAME, D.DEPARTMENT_NAME
FROM EMPLOYEES E
JOIN DEPARTMENTS D ON E.DEPARTMENT_ID = D.DEPARTMENT_ID
ORDER BY E.DEPARTMENT_ID, D.DEPARTMENT_ID;
- 두 테이블을 DEPARTMENT_ID 기준으로 정렬한 후,
- 정렬된 상태에서 병합(merge)하여 조인 수행.
4️⃣ Sort Merge Join의 장점과 단점
✅ 장점
✔ 인덱스가 없어도 효율적
✔ 모든 비교 연산(=, <, >, BETWEEN)에서 사용 가능
✔ 대량 데이터에서 효과적, 특히 정렬된 경우 더욱 빠름
✔ 순차적인 디스크 접근으로 랜덤 I/O 감소
❌ 단점
✖ 정렬(Sort) 단계가 필요하므로 추가적인 비용 발생
✖ 데이터가 정렬되어 있지 않으면 성능 저하 가능
✖ 메모리 사용량이 많을 수 있음
🔹 조인 방식 비교
조인 방식 | 인덱스 필요 여부 | 사용 가능한 조건 | 성능 특징 |
Nested Loop Join | ✅ 필요 (인덱스 없으면 비효율적) | ✅ 모든 비교 연산 (=, <, >, BETWEEN) 가능 | 작은 데이터에 적합, 인덱스 없으면 Full Scan 발생 |
Sort Merge Join | ❌ 필요 없음 (정렬 필요) | ✅ 모든 비교 연산 (=, <, >, BETWEEN) 가능 | 대량 데이터에서 유리, 정렬된 경우 매우 빠름 |
Hash Join | ❌ 필요 없음 | ❌ = (동등 조인)만 가능 | 대량 데이터에서 효과적, CPU/메모리 사용 높음 |
🔹 결론
- Nested Loop Join:
- 소량의 데이터에 적합.
- 내부 테이블에 인덱스가 있으면 빠름, 하지만 없으면 비효율적.
- 랜덤 I/O 발생 가능 → 디스크 I/O 성능에 영향을 받을 수 있음.
- Sort Merge Join:
- 대량의 데이터에 적합.
- 모든 비교 연산 가능(=, <, >, BETWEEN).
- 정렬 비용이 있지만, 정렬된 데이터에서는 매우 빠름.
- 순차적인 디스크 접근으로 I/O 성능이 우수.
- Hash Join:
- 인덱스 없이 대량 데이터를 조인할 때 효과적.
- 메모리 사용량이 많고, CPU 연산 부담이 크므로 신중하게 사용해야 함.
- 동등 조인(=)에서만 사용 가능.
💡 도움이 되셨다면 댓글과 공감 부탁드립니다! 😊
📌 더 많은 알고리즘 풀이와 프로그래밍 자료는 블로그에서 확인하세요!
✉️ 문의나 피드백은 댓글이나 이메일로 남겨주세요.
'자격증 > SQLD' 카테고리의 다른 글
SQLD 84점 합격 리뷰 ( 난이도, 독학 방법 및 자료) (0) | 2025.03.28 |
---|---|
[SQLD] 오답 노트 및 핵심 문제 (0) | 2025.02.28 |
[SQLD SP01]JOIN에서 ON과 WHERE 차이 (0) | 2025.02.26 |
[SQLD] 5-2: 데이터 정의어(DDL) & 데이터 제어어(DCL) (0) | 2025.02.22 |
[SQLD] 5-1: 데이터 조작어 (DML) 와 트랜잭션 제어(TCL) (0) | 2025.02.22 |