안녕하세요.
해쉬조인 힌트를 알고서 써먹어보니 NL조인과 속도 차이가 어마어마 하더라구요.
주로 배치성 sql에 쓰고 있긴 하지만요..
생각없이 여러개 테이블 조인할때 아래와 같이 하면 10분 이상 걸리던게 1분이면 나오더라구요.
/*+ leading(a b c) use_hash(b c) */
OLTP 성에 쓰면 메모리와 cpu를 많이 써서 조심해야 된다고 하지만,
유혹에서 벗어나질 못하겠더라구요.ㅠ.ㅠ
마구잡이로 쓰는거보다 좀 내부적으로 어떻게 해쉬테이블(메모리)에 올리는지 궁금합니다.
성능고도화2 책에서 보니 A가 B와 조인하기 위해서 B와 조인할 A의 컬럼을 메모리에 올리고 B와 해시조인하고
A,B랑 조인 결과를 메모리에 올리고 C와 해시 조인한다 라고 제가 이해를 했는대
그렇다면 C와 조인하기 위해서 A,B 결과값이 100만건이면 100만건 다 메모리에 올라 가나요?
아님 조인할때 건건이 메모리에 올렷다가 조인하고 메모리 해제 하고 그러나요?
질문이 두서가 없는대 해시 조인시 해시테이블(메모리)에 얼마 만큼에 양이 올라가는지 궁금 합니다.
마구잡이로 썻다가 힌트 때문에 시스템 버벅 거리는 상황이 올수도 있을거 같아서요.
제가 아는 대로 서술해봅니다. (DBMS가 오라클이라는 가정하에)
Q. A,B 조인 결과 값, (100만 건)이 다 메모리에 건건이 올라가나요?
네, 다올라갑니다. 하지만 공유 메모리 즉, SGA의 buffer cache 영역을 사용하는 것이 아니라, 명령어를 수행한 유저의 프로세서에 할당된 메모리를 사용합니다. PGA라고 하지요.
추가로, hash 조인할 때 driving 되는 테이블을 올리고자 하나, PGA에 할당된 메모리크기를 벗어난다고 하면 그 때 temp tablespace를 사용합니다.
만일, temp tablespace 를 사용한다고 하면 hash 조인의 성능이 약간은 저하되어 결과가 리턴됩니다.
oracle에서는 hash 조인 시 temp tablespace를 사용하지 않으려고 아래와 같은 파라미터를 통해 사이즈를 조절합니다.
※ HASH_AREA_SIZE
해쉬 조인할 때 PGA에 드라이빙할 수 있는 공간의 크기 설정