- h2. Consistent 모드 읽기와 Current 모드 읽기의 차이점
읽기 구분 | 기준 시점 | SQL Trade | Autotrace | 비고 |
---|
Consistent 모드 | 쿼리가 시작된 시점(쿼리 SCN)을 기준으로 액세스 | query | consistent gets | |
Current 모드 | 레코드를 찾아간 바로 그 시점 기준으로 액세스 | current | db block gets | 쿼리 SCN, 블록 SCN 을 비교하지 않으며 커밋된 값 사용 DML, 대량 데이터 정렬(디스크 소트 사용시)시 발생 |
- h2. Consistent 모드로 갱신할 때 생기는 현상 : Lost Update
- 데모 #1
TX1 | | TX2 |
---|
update emp set sal = sal + 100 where empno = 7788; | t1 | |
| t2 | update emp set sal = sal + 200 where empno = 7788; |
commit; | t3 | |
| t4 | commit; |
- select sal from emp where empno = 7788;
- Consistent 모드 → [1200]
- 오라클 → [1300]
- h2. Current 모드로 갱신할 때 생기는 현상 : 일관성 문제
- 데모 #1
TX1 | | TX2 |
---|
update emp set sal = 2000 where empno = 7788 and sal = 1000; | t1 | |
| t2 | update emp set sal = 3000 where empno = 7788 and sal = 2000; |
commit; | t3 | |
| t4 | commit; |
- select sal from emp where empno = 7788;
- Current 모드 → [3000]
- Cybase, SQL Server 는 이렇게 동작
- 오라클 → [2000]
- 데모 #2
TX1 | | TX2 |
---|
update t set no = no + 1 where no > 50000; | t1 | |
| t2 | insert into t values ( 100001, 100001 ); |
| t3 | commit; |
commit; | t4 | |
- TX1의 SQL%ROWCOUNT 는?
- Current 모드 → [50001]
- 오라클 → [50000]
- h2. Consistent 모드로 읽고, Current 모드로 갱신할 때 생기는 현상
- 데모 #1
TX1 | | TX2 |
---|
update emp set sal = sal + 100 where empno = 7788 and sal = 1000; | t1 | |
| t2 | update emp set sal = sal + 200 where empno = 7788 and sal = 1000; |
commit; | t3 | |
| t4 | commit; |
- select sal from emp where empno = 7788;
- Consistent 모드로 읽고, Current 모드로 갱신 → [1300]
- 오라클 → [1100]
- 데모 #2
① | update emp set sal = sal + 200 |
| where empno = 7788 |
| and sal = 1000; |
| |
② | update |
| ( |
| select sal from emp |
| where empno = 7788 |
| and sal = 1000 |
| ) |
| set sal = sal + 200; |
- 빨간건 Consistent 모드로 읽고, 파란건 Current 모드로 읽는건 아니다.
- h2. Consistent 모드로 갱신대상을 식별하고, Current 모드로 갱신
- 데모 #1 (사실은...)
for c in | 모드 |
( | |
select rowid rid from emp | Consistent |
where empno = 7788 and sal = 1000 | |
) | |
loop | |
update emp set sal = sal + 200 | Current |
where empno = 7788 | |
and sal = 1000 | |
and rowid = c.rid; | |
end loop; | |
- h2. 오라클에서 일관성 없게 값을 갱신하는 사례
SQL | 계좌1.잔고 읽기 모드 | 계좌2.잔고 읽기 모드 | 비고 |
---|
update 계좌2 set 총잔고 = 계좌2.잔고 + (select 잔고 from 계좌1 where 계좌번호 = 계좌2.계좌번호) where 계좌번호 = 7788; | Consistent | Current | 쿼리 SCN 이후에 계좌1의 변동 내역이 무시됨 |
update 계좌2 set 총잔고 = (select 계좌2.잔고 + 잔고 from 계좌1 where 계좌번호 = 계좌2.계좌번호) where 계좌번호 = 7788; | Current | Current | 계좌1의 현재값을 읽으나, delete 된경우 NULL 로 업데이트 됨 |
- 스칼라 서브쿼리는 특별한 이유가 없는 한 항상 Consistent 모드로 읽는다
참조문서
서적(오라클 성능 고도화 원리와해법 I) : http://book.daum.net/detail/book.do?bookid=KOR9788996246015