들어가며
관계형 데이터베이스에서 여러 테이블의 데이터를 함께 활용하기 위해선 SQL JOIN에 대해 알아야 합니다. 이를 통해 데이터 간의 관계를 효과적으로 활용하여 효율적으로 데이터를 검색할 수 있습니다. 👍 해당 포스팅에서는 다양한 JOIN의 유형과 그 사용법, 주의해야 할 점에 대해 다룹니다.
❏ JOIN의 개념 및 JOIN의 종류
JOIN이란 두 개 이상의 테이블을 연결하여 원하는 데이터를 조회하는 방법을 말합니다.
따라서, 정규화된 데이터베이스 구조에서 분산된 데이터를 결합하여 원하는 데이터를 도출할 수 있습니다.
❍ INNER JOIN
INNER JOIN은 두 테이블에서 조건이 일치하는 행만을 결과로 반환합니다. 따라서 두 테이블에 모두 지정한 열의 데이터가 존재해야 합니다.
예시
SELECT 학생.이름, 과목.과목명, 수강.학점
FROM 학생
INNER JOIN 수강 ON 학생.학생_id = 수강.학생_id
INNER JOIN 과목 ON 수강.과목_id = 과목.과목_id;
→ 학생이 수강한 과목과 그 학점을 조회합니다. 수강 기록이 없는 학생이나 수강생이 없는 과목은 결과에 포함되지 않습니다.
장점
- 데이터의 정확성이 보장됩니다.
단점
- 조건에 맞지 않는 데이터는 모두 제외됩니다.
INNER JOIN은 두 테이블 간의 관계가 확실할 때 사용해주면 적절하게 사용할 수 있습니다.
INNER JOIN은 두 테이블에 모두 데이터가 있어야만 결과를 가져올 수 있지만, OUTER JOIN의 경우 한쪽에만 데이터가 있어도 결과를 가져올 수 있습니다.
❍ LEFT (OUTER) JOIN
LEFT JOIN은 왼쪽 테이블의 모든 행을 포함하고, 오른쪽 테이블에서 조건에 맞는 행을 결합하여 결과로 반환합니다. 조건에 맞는 행이 없는 경우엔 NULL로 값이 채워집니다.
예시
SELECT 학생.이름, 과목.과목명
FROM 학생
LEFT JOIN 수강 ON 학생.학생_id = 수강.학생_id
LEFT JOIN 과목 ON 수강.과목_id = 과목.과목_id;
→ 모든 학생을 보여주며, 수강하는 과목이 있다면 그 과목도 함께 표시합니다. 수강 과목이 없는 학생도 결과에 포함됩니다.
장점
- 왼쪽 테이블의 모든 데이터를 유지할 수 있습니다
단점
- 불필요한 NULL값이 많이 생길 수 있습니다.
LEFT JOIN은 모든 레코드를 포함해야 하는 경우에 적절하게 사용할 수 있습니다.
❍ RIGHT (OUTER) JOIN
RIGHT JOIN은 LEFT JOIN의 반대로, 오른쪽 테이블의 모든 행을 포함하고 왼쪽 테이블에서조건에 맞는 행을 결합하여 결과로 반환합니다. 마찬가지로 조건에 맞지 않는 경우엔 NULL로 값이 채워집니다.
예시
SELECT 과목.과목명, 학생.이름
FROM 수강
RIGHT JOIN 과목 ON 수강.과목_id = 과목.과목_id
LEFT JOIN 학생 ON 수강.학생_id = 학생.학생_id;
→ 모든 과목을 보여주며, 수강하는 학생이 있다면 그 학생도 함께 표시합니다. 수강생이 없는 과목도 결과에 포함됩니다.
❍ FULL (OUTER) JOIN
FULL JOIN은 LEFT JOIN과 RIGHT JOIN을 합한 것으로, 양쪽 테이블의 모든 행을 포함하고 일치하지 않는 행의 경우엔 NULL로 값이 채워집니다.
예시
SELECT 학생.이름, 과목.과목명
FROM 학생
FULL JOIN 수강 ON 학생.학생_id = 수강.학생_id
FULL JOIN 과목 ON 수강.과목_id = 과목.과목_id;
→ 모든 학생과 모든 과목을 보여줍니다. 수강하지 않는 학생과 수강생이 없는 과목도 모두 결과에 포함됩니다.
장점
- 두 테이블의 모든 데이터를 한 번에 확인할 수 있습니다.
단점
- 대량의 NULL값이 많이 생길 수 있습니다.
FULL JOIN은 반드시 두 테이블의 모든 데이터의 비교가 필요한 경우에 적절하게 사용할 수 있습니다.
❍ CROSS JOIN
CROSS JOIN은 두 테이블의 모든 가능한 조합을 만들어 결과로 반환합니다. 카테시안곱(Cartesian product)로 두 테이블의 각 행의 개수를 곱한 값이 전체 행의 개수가 됩니다.
예시
SELECT 학생.이름, 과목.과목명
FROM 학생
CROSS JOIN 과목;
→ 학생 테이블과 과목 테이블의 모든 데이터를 조합한 결과가 도출됩니다. 학생 테이블의 데이터 개수가 5개, 과목 테이블의 데이터 개수가 5개. 총 도출되는 결과의 값은 25개가 됩니다.
장점
- 모든 가능한 조합을 생성할 수 있습니다.
단점
- 결과가 매우 커질 수 있으므로 성능에 영향을 줄 수 있습니다.
❍ SELF JOIN
SELF JOIN은 자기 자신과 조인하는 방식입니다.
예시
SELECT a.이름 AS 학생1, b.이름 AS 학생2, a.학과
FROM 학생 a
JOIN 학생 b ON a.학과 = b.학과 AND a.학생_id < b.학생_id;
→ 학생 테이블을 자기 자신과 조인하여 같은 학과의 학생을 매칭한 결과가 도출됩니다.
장점
- 같은 테이블 내의 관계를 표현할 수 있습니다.
단점
- 복잡한 쿼리가 될 수 있으므로 성능에 주의해야 합니다.
SELF JOIN은 주로 계층 구조이거나 순서가 있는 데이터를 다루는 경우에 적절하게 사용할 수 있습니다.
❍ JOIN 최적화
- 상황에 맞는 적절한 JOIN 유형 선택
- 필요한 데이터만 JOIN하는 것이 성능적으로 좋음
- JOIN 수행 전, WHERE 절 및 중복 제거로 데이터 필터링
❏ LEFT JOIN에서의 주의할 점
1. 테이블 순서의 중요성
가장 많은 열을 가져와야 하는 테이블을 우선적으로 명시해야 합니다.
그 이유는 왼쪽에 오는 테이블의 모든 행이 결과에 포함되므로, 기준이 되는 테이블을 먼저 작성합니다.'
2. JOIN 순서에 주의
LEFT JOIN 이후에 INNER JOIN이 나오면 안됩니다.
LEFT JOIN에서 INNER JOIN 조건에 일치하지 않는 경우가 발생하며 결과제 제외가 됩니다. 따라서, INNER JOIN을 사용하게 되면 LEFT JOIN의 수행 의도가 무시될 수 있습니다.
3. 1:N 관계에서의 중복
1:N 관계에서 LEFT JOIN을 사용하면 데이터 중복이 발생할 수 있습니다. 오른쪽 테이블에서의 데이터가 중복으로 있는 경우, 결과 테이블에서도 중복이 발생하게 됩니다.
- DISTINCT를 사용해서 중복 제거
- GROUP BY를 사용하여 집계
- 서브 쿼리나 조인 조건을 수정하여 중복 방지
의 방법을 적절히 사용하여 중복을 처리해주도록 합니다.
4. NULL 값 처리
LEFT JOIN은 왼쪽 테이블의 모든 행을 포함하고 오른쪽 테이블에 조건에 맞는 행이 없으면 NULL값이 반환되므로, 이에 대한 적절한 처리가 필요합니다. (IS NULL, IS NOT NULL로 필터링)
5. 성능 고려
INNER JOIN에 비해 더 많은 연산이 수행되는 LEFT JOIN은 성능에 영향을 줄 수 있습니다. 따라서, INNER JOIN의 사용이 가능하다면 INNER JOIN을 사용하는 것이 성능 면에서 유리할 수 있습니다.
https://hongong.hanbit.co.kr/sql-기본-문법-joininner-outer-cross-self-join/