보통 조인으로 풀기 어려울 경우나 쿼리의 단순화를 위해 함수를 사용합니다.
그런데 그 함수가 여러개의 값을 리턴해야 할 경우 각각에 대한것을 함수로 만들게 되죠
예를 들면
품목아이디, 품목명, 품목코드 등..
SLELECT F_GET_ITEM_CODE(ITEM_ID ) AS ITEM_CODE
, F_GET_ITEM_DESC(ITEM_ID ) AS ITEM_DESC
, F_GET_ITEM_SPEC(ITEM_ID ) AS ITEM_SPEC
, ITEM_ID
FROM 판매이력;
이 함수가 좀 복잡하여 시간을 소요한다고 할때
위와 같이 사용하는 것이 속도면에서 나은가요? 아니면 아래와 같이 사용하는 것이 나을까요?
SELECT SUBSTR( ITEM_NAME_DESC, 1,10 ) AS ITEM_NAME
, SUBSTR( ITEM_NAME_DESC, 11,10 ) AS ITEM_DESC
, SUBSTR( ITEM_NAME_DESC, 13,10 ) AS ITEM_SPEC
, ITEM_ID
FROM (
SLELECT /*+ NO_MERGE */
F_GET_ITEM_CODE_DESC(ITEM_ID ) AS ITEM_NAME_DESC
, ITEM_ID
FROM 판매이력);
※ 마농님의 조언에 따라 한번만 호출하는 효과를 얻기 위해 위와 no_merge 힌트를 추가하였습니다.
no_merge 를 사용하지 않으면 1 과 똑같습니다...
제 3의 방법으로는 PIPE FUNCTION 이 있습니다. 여러값을 조인한것처럼 한번에 받아 올수 있죠.
SELECT T.ITEM_NAME AS ITEM_NAME
, T.ITEM_DESC AS ITEM_DESC
, T.ITEM_SPEC AS ITEM_SPEC
, ITEM_ID
FROM 판매이력
LFET JOIN TABLE(TAB_FUNC(ITEM_ID)) T
ON 판매이력.ITEM_ID = T.ITEM_ID;
각각마다 장단점이 있는데
1번 방법은 가져오는 함수가 완전히 구분되어 있어 명확하다는 것이고, 속도상은 좀 불리하죠. 여러번 함수를 호출해야 하니.
2번 방법은 함수에서 여러개의 값을 구분자로 묶어 하나로 호출한 뒤 뒤에서 잘라써야 한는 불편함이 있지만
호출은 한번만 할것 같아서 속도면에서 1번 보다 나아 보이고요. ( 단 no_merge 힌트 추가시)
3.번 방법은 다중으로 리턴값을 받을 수 있어 편리할 수 있지만 펑션(1,2) 보다 속도가 약간 떨어지는 듯 하더군요.
여러분은 어떤 방법을 선호하시는지?
PS) 예제로 간략하게 만들었으니 약간의 오류는 무시하여 주세용 ^^