부분범위 처리
= 처리할 내용이 아무리 많더라도 일단 운반단위에 차게 되면 데이터를 RETURN시키고,
사용자가 다음 ACTION을 취할 때까지 기다리므로 처리범위의 크기에 영향을 받지 않도록 하는 기법
- 조건을 만족하는 전체 집합이 아닌 일부분만 엑세스
- 데이터량이 많아도 퍼포먼스에 지정이 없고, 오히려 향상
- 인덱스나 클러스터를 적절히 활용한 소트의 대체(ORDER BY 를 안하도록 한다.)
그 외..
- 테이블을 엑세스하지 않고 인덱스만 사용하도록 유도
- EXIST의 활용(IN 보다 효율적, EXISTS 는 옵티마이저가 부분범위처리한다.)
- ORDER BY 생략(불필요한 정렬작업 생략)
- MIN / MAX
- ROWNUM의 활용 -> STOP KEY 를 이용
- QUERY를 이원화 하여 일부분씩 스캔 하도록 유도(소트의 범위를 줄임)
등의 활용예를 통해 부분범위 처리를 확인해 볼 수 있다.
옵티마이저 힌트는 적대적인 것은 아니다. 힌트를 줘 놓고 힌트를 쓸수 있는 요소가 없으면 힌트가 사용되지 않는다.
때문에 멍텅구리 조건을 주는 경우가 있다.
- 인덱스가 있는 컬럼을 조건절에 넣는다.(단, 추출하려는 데이터에 영향을 미치지 않는 한도내에서.)
* 전체범위처리 : FULL RANGE SCAN 후 가공하여 ARRAY SIZE 만큼 추출
* 조건을 만족하는 ROW 수가 ARRAY SIZE에 도달되면 멈춤(STOP KEY)
*/
/*
SORT 를 대신하는 인덱스
*/
-- 싱글 인덱스
-- SELECT * FROM PRODUCT WHERE YMD = '951023' AND ITEM LIKE 'AB%' ORDER BY YMD, ITEM;
-- 결합 인덱스
-- SELECT * FROM PRODUCT WHERE YMD = '951023' AND ITEM LIKE 'AB%';
/*
INDEX 생성
*/
-- create index HIREDATE_IDX ON EMPLOYEES(HIRE_DATE)
/*
MAX 처리
*/
-- SELECT MAX(HIRE_DATE) FROM EMPLOYEES;
-- SELECT /*+INDEX_DESC(EMPLOYEES HIREDATE_IDX) */ HIRE_DATE FROM EMPLOYEES WHERE HIRE_DATE < '20/12/30' AND ROWNUM = 1;
-- SELECT MAX(EMPLOYEE_ID)+ 1 FROM EMPLOYEES WHERE DEPARTMENT_ID = 100;
-- SELECT /*+INDEX_DESC(EMPLOYEE_ID) */ EMPLOYEE_ID + 1 FROM EMPLOYEES WHERE DEPARTMENT_ID = 100 AND ROWNUM = 1;
/*
EXISTS
*/
-- SELECT COUNT(*) FROM hr.EMPLOYEES WHERE DEPARTMENT_ID = 100 AND EMPLOYEE_ID > 10 ;
-- SELECT 1 FROM DUAL WHERE EXISTS(SELECT 'X' FROM EMPLOYEES WHERE DEPARTMENT_ID = 100 AND EMPLOYEE_ID < 10);
/*
범위가 좁은것 부터 큰 것으로 조건을 지정
*/
-- select * from employees where employee_id between 10 and 10000 and department_id = '100';
-- select /*+index_asc(department_id, employee_id)*/ * from employees
-- where department_id = '100' and employee_id between 10 and 10000 ;
/*
인덱스를 최대한 활용하라.
*/
-- select min(salary) from employees;
-- select min(salary) from employees where salary > 0 and rownum = 1;
/*
부분범위 처리가능시 최초운반단위를 빨리 채우도록 한다.
*/
-- select last_name, salary * 100 from employees where hire_date like '9%' order by last_name;
-- select last_name, salary * 100 from employees where hire_date like '9%' and last_name > ' ' ;
/*
UNION 대신 UNION ALL을 사용하라.
*/
-- select last_name, salary * 100 from employees where hire_date like '96%'
-- union
-- select last_name, salary * 100 from employees where hire_date not like '96%' ;
-- select last_name, salary * 100 from employees where hire_date like '96%'
-- union all
-- select last_name, salary * 100 from employees where hire_date not like '96%' ;
Posted by 홍반장