오라클에서 제공하는 PIVOT 은 이해하기도 난해 하고 딱 보면 와닿지가 않고
어느컬럼이 축이 되는지, group by 도 자돋 처리 되어 버리고 ,
이것저것해봐야 이해 되서 어떤때 써야 효과가 나오는지 모르겠습니다.
PIVOT 에 있는 in 절을 select 가 가능하면 프로그램 별도 코딩없이 가능한대 그게 안되니 반쪽 짜리 같네요.
어차피 코딩이 들어갈거면 옛날 방식으로 짜고 펼칠 컬럼은 코딩으로 처리 하는게 더 직관적이네요.
그리고 아래 처럼 null이 있으면 계산 오류도 발생하고..
-- job별 부서,mgr별 합계 구하기 1
SELECT a.job
, SUM(CASE WHEN deptno = '10' AND mgr = '7839' THEN sal ELSE NULL END) AS aaa101
, SUM(CASE WHEN deptno = '10' AND mgr = '7782' THEN sal ELSE NULL END) AS aaa102
, SUM(CASE WHEN deptno = '10' AND mgr IS null THEN sal ELSE NULL END) AS aaa103
, SUM(CASE WHEN deptno = '20' AND mgr = '7839' THEN sal ELSE NULL END) AS bbb204
, SUM(CASE WHEN deptno = '20' AND mgr = '7566' THEN sal ELSE NULL END) AS bbb205
, SUM(CASE WHEN deptno = '20' AND mgr = '7902' THEN sal ELSE NULL END) AS bbb206
, SUM(CASE WHEN deptno = '20' AND mgr = '7788' THEN sal ELSE NULL END) AS bbb207
, SUM(CASE WHEN deptno = '30' AND mgr = '7698' THEN sal ELSE NULL END) AS ccc308
, SUM(CASE WHEN deptno = '30' AND mgr = '7839' THEN sal ELSE NULL END) AS ccc309
, sum(sal)
FROM emp a
GROUP BY job
-- job별 부서,mgr별 합계 구하기 2
SELECT *
FROM (
SELECT
a.deptno
, a.sal
, a.job
, a.mgr
FROM emp a
)
PIVOT (
sum(sal) FOR (deptno, mgr )IN (
(10, 7839) aaa101,
(10, 7782) aaa102,
(10, NULl) aaa103, -- null 은 계산이 안되어 오류 발생
(20, 7839) bbb204,
(20, 7566) bbb205,
(20, 7902) bbb206,
(20, 7788) bbb207,
(30, 7698) ccc308,
(30, 7839) ccc309
)
)
;
구문들은 장단점을 가지고 있습니다.
PIVOT 은 기존 MIN(DECODE 구문을 단순화 시켜 간결한 구문을 작성할 수 있습니다.
다만 구문이 좀 딱딱하다고 할까요? 정해진 틀에 맞게 작성해야 합니다.
유연성으로 보면 이전 구문이 더 유연합니다.
행을 열로 바꾸는 피벗쿼리는(기존 MIN(DECODE()) 방식과 PIVOT 구문 둘다)
열로 바꿀 항목의 개수와 각각의 값을 정확히 알고 있어야 합니다.
아직까지는 가변값을 적용해주는 쿼리는 없습니다.
가변적으로 적용하려면 동적으로 구현해야 합니다.
PIVOT XML 구문을 사용할 경우 서브쿼리를 IN 절로 사용이 가능하긴 한데
결과가 XML 형태로 나옵니다.
요구사항이 단순한 경우 PIVOT 구문이 쿼리가 간결하고
요구사항이 복잡한 경우 PIVOT 구문은 한계가 있어 이전 구문이 좋습니다.