JOIN vs UNION ALL
JOIN과 UNION은 모두 두 개 이상의 테이블을 합칠 때 사용되지만, 사용 방식과 결과가 다르다.
- JOIN
JOIN은 기본적으로 두 테이블에서 공통된 값을 기준으로 행을 합친다. 테이블 사이에 관계를 설정하고, 그 관계를 기반으로 테이블을 합치려는 경우 주로 사용된다. -> ex) 고객 테이블과 주문 테이블
- UNION ALL
두 개 이상의 SELECT문 결과를 단순히 위아래로 합친다. 두 테이블이 동일한 열 구조(Column의 갯수와 타입)를 가지고 있으며, 모든 행을 하나의 테이블로 합치려는 경우 주로 사용된다.
아래의 아이스크림 예제의 경우 FIRST_HALF와 JULY 테이블이 동일한 열 구조(FLAVOR, TOTAL_ORDER를 포함)를 가지고 있기 때문에 두 테이블의 모든 행을 하나의 큰 테이블로 합치는 것이 직관적이다.
또한, 같은 FLAVOR의 주문이 다른 ID로 주문 발생했을 경우 각각의 발생을 모두 포함할 수 있고, JULY 테이블에는 FIRST_HALF 테이블에 없는 FLAVOR가 있을 수 있으므로, JOIN을 사용하면 이런 정보가 누락될 수 있다.
UNION (ALL)
SELECT FLAVOR
FROM (
SELECT FLAVOR, SUM(TOTAL_ORDER) AS TOTAL_SUM
FROM (
SELECT FLAVOR, TOTAL_ORDER FROM FIRST_HALF
UNION ALL
SELECT FLAVOR, TOTAL_ORDER FROM JULY
) AS ALL_ORDERS // 두 테이블의 모든 행 결합
// UNION ALL: 두 테이블의 모든 행 포함, 중복된 행도 포함
GROUP BY FLAVOR
// 결합한 테이블을 기반으로 같은 맛에 대한 total_order의 합을 계산
ORDER BY TOTAL_SUM DESC
LIMIT 3
) AS TOP_FLAVORS;
-> 정답 쿼리
- 두 테이블을 union all을 이용해 중복된 행까지 포함하여 결합한다. -> ALL_ORDERS
- 결합된 테이블에서 flavor로 그룹화 시킨다. (group by)
- select절에 sum(total_order) 집계 함수를 포함시키고, order by와 limit을 이용해 3개를 질의한다.
- 질의한 내용을 최상단 select절의 flavor에 담는다.
UNION ALL
두 select문의 결과를 합치고, 중복된 행을 제거하지 않는다. 즉, 모든 행을 결과에 포함한다.
(apple, banana, cherry, apple, banana, cherry)
UNION
두 select문의 결과를 합치고, 중복된 행을 제거한다.
(apple, banana, cherry)
JOIN
1. INNER JOIN
교집합의 데이터만 연결시켜주고 나머지는 버린다.
-- SELECT [별칭.필드1], [별칭.필드2]... FROM [Table 이름] AS [별칭] INNER JOIN [Table 이름] AS [별칭] ON [조건]
SELECT a.myAge, a.myName, b.myId FROM mytable AS a INNER JOIN testtable AS b on a.myname = b.myname
2. LEFT (OUTER) JOIN
왼쪽 테이블은 모두 포함, 오른쪽 테이블은 교집합 부분만 포함한다.
일치하는 행이 없을 경우 NULL로 채워진다.
-- SELECT [별칭.필드1], [별칭.필드2]... FROM [Table 이름] AS [별칭] LEFT OUTER JOIN [Table 이름] AS [별칭] ON [조건]
SELECT a.myAge, a.myName, b.myId FROM mytable AS a LEFT OUTER JOIN testtable AS b on a.myname = b.myname
3. CROSS JOIN
두 데이터의 모든 경우의 수
-- SELECT [별칭.필드1], [별칭.필드2]... FROM [Table 이름] AS [별칭] CROSS JOIN [Table 이름] AS [별칭]
SELECT a.myAge, a.myName, b.myId FROM mytable AS a CROSS JOIN testtable AS b
-- SELECT [별칭.필드1], [별칭.필드2]... FROM [Table 이름] AS [별칭], [Table 이름] AS [별칭]
-- CROSS JOIN 대신 ,(콤마) 로도 가능
SELECT a.myAge, a.myName, b.myId FROM mytable AS a, testtable AS b
참고 자료
'SQL' 카테고리의 다른 글
[MySQL] GROUP BY & HAVING (0) | 2023.12.06 |
---|---|
[MySQL] 서브 쿼리 IN & INNER JOIN (0) | 2023.11.29 |