UNION을 사용한 조건 분기는 성능적 측면에서 단점을 가지고 있습니다. 하나의 SQL구문 이지만 내부적으로는 여러개의 SELECT 구문을 실행하는 실행 계획으로 해석되기 때문입니다. 따라서 테이블에 접근하는 횟수가 많아집니다.
SELECT item_name, year, price_tax_ex AS price
FROM items
WHERE year <= 2001
UNION ALL
SELECT item_name, year, price_tax_ex AS price
FROM items
WHERE year >= 2002;
위의 코드는 쓸데없이 길고 같은 쿼리를 두번이나 실행하고 있음.
=> SELECT 구문 전체를 여러번 사용해서 코드를 길게 만드는 것은 쓸데없는 테이블 접근을 발생시킴
"조건 분기를 WHERE구로 하는 사람들은 초보자"
SELECT item_name, year,
CASE WHEN year <= 2001 THEN price_tax_ex
WHEN year >= 2002 THEN price_tax_ex EMD AS price
FROM Items;
위의 코드는 UNION을 사용한 쿼리와 같은 결과를 출력하지만 성능은 훨씬 좋습니다.
UNION을 사용한 분기는 절차지향적, CASE를 사용한 분기는 '식'을 바탕으로 하는 사고
SELECT prefecture, SUM(pop_men) AS pop_men, SUM(pop_men) AS pop_men
FROM (SELECT prefecture, popAS pop_men, null AS pop_wom
FROM Population
WHERE sex = '1'
UNION
SELECT prefecture, NULL AS pop_men, pop AS pop_wom
FROM Popluation
WHERE sex = '2' )TMP
GROUP MY prefecture;
WHERE 구에서 sex 필드로 분기하고, 결과를 UNION 로 머지 한다는 절차 지향적 구성
Population 테이블에 풀 스캔 2회 수행됩니다.
SELECT prefecture,
SUM (CASE WHEN sex = '1' THEN pop ELSE 0 END) AS pop_men,
SUM (CASE WHEN sex = '2' THEN pop ELSE 0 END) AS pop_wom
FROM Population
GROUP BY prefecture;
population 테이블 풀 스캔이 1회로 감소,
SELECT emp_name,
MAX(team) AS team
FROM Employees
GROUP BY emp_name
HAVING COUNT(*) = 1
UNION
SELECT emp_name,
'2개를 겸무' AS team
FROM Employees
GROUP BY emp_name
HAVING COUNT(*) =2
WHERE 구와 다르지않음
SELECT emp_name,
CASE WHEN COUNT(*) =1 THEN MAX(team)
WHEN COUNT(*) =2 THEN '2개를 겸무'
END AS team
FROM Employees
GROUP BY emp_name;
HAVING 구에서 조건 분기하는 것도 초보자!