天天看點

***oracle點知識4——事務表

<a href="http://www.itpub.net/thread-942639-1-1.html">http://www.itpub.net/thread-942639-1-1.html</a>

復原段頭中,有一項非常重要的資訊,就是事務表。對事務表頻繁的通路,可能會造成復原段頭的争用.了解什麼樣的操作會通路事務表,對于了解復原段頭争用的原因非常重要.下面我們來做一些實驗來驗證一下,什麼樣的操作才會通路事務表.

    首先簡單介紹一個視圖,備份x$bh.對這個視圖我想大家都有一定的了解,bh即buffer header 的簡寫.在buffer  header中有一個TCH 列,表示塊被通路的次數.我們通過他來驗證事務表什麼時候被通路.需要注意的是.TCH列每3秒,才會重新計算一次,3秒之内無論通路某一個塊多少次.TCH列隻會增加1.

  在會話A開啟一個事務後:

步驟一:通過v$transaction視圖找到XID

SQL&gt; select xidusn,ubablk,ubafil from v$transaction;

    XIDUSN     UBABLK     UBAFIL

----------       ----------     ----------

        13            97             5

步驟二:通過復原段編号,可得知事務所占復原段名,并用此查找事務頭塊号,檔案号

SQL&gt; select header_block,header_file from dba_segments where segment_name='_SYSSMU13$';

HEADER_BLOCK    HEADER_FILE

------------                  -----------

          41                          5

步驟三:檢視x$bh視圖中,TCH值的增加.

SQL&gt; select addr,tch from x$bh where dbarfil=5 and dbablk=41;

ADDR                TCH

--------          ----------

080B5208         41

步驟四:查找完TCH後,馬上執行要測試的指令(會話B),

SQL&gt; select * from jj_3;

        ID NA

---------- --

         1 aa

         2 aa

         3 aa

         4 aa

         5 CN

步驟五:再次檢視x$bh視圖

ADDR            TCH

-------- ----------

080B5208         42

    小結:從結果集來看,在另一會話中通路未送出資料的select語句會通路事務表,那麼其他的DML操作呢?(希望大家也都試試,我的結果是都會增加TCH值).上面我的步驟四是全表掃描.

    如果我的表有兩個塊,分别是塊一塊二,在塊一中修改行A,按照rowid通路塊一中的行B,這樣會通路事務表嗎?如果

按照rowid通路塊二中的行,會通路事務表嗎?下面我來實驗下看結果是什麼:

步一:利用函數檢視該表的塊号.

SQL&gt; select rowid,dbms_rowid.rowid_block_number(rowid) from jj_3;

ROWID                             DBMS_ROWID.ROWID_BLOCK_NUMBER(ROWID)

------------------                                ------------------------------------

AAAMvjAAKAAAAEdAAA                                  285

AAAMvjAAKAAAAEdAAB                                  285

AAAMvjAAKAAAAEdAAC                                  285

AAAMvjAAKAAAAEeAAA                                  286

步二: 在B會話中通過AAAMvjAAKAAAAEdAAC修改表.

SQL&gt; update jj_3 set id=10 where rowid='AAAMvjAAKAAAAEdAAC';

已更新 1 行。

步三: 在A會話中通過AAAMvjAAKAAAAEdAAA檢視行

SQL&gt; select * from jj_3 where rowid='AAAMvjAAKAAAAEdAAA';

在做步一和二之前,先檢視一下X$BH,因為他會因為oracle的内部操作而增加,

實驗前檢視結果:

ADDR                      TCH

--------                ----------

080B51BC              63

實驗後檢視結果:

--------           ----------

080B51BC         64

  結論一:在塊一中修改行A,按照rowid通路塊一中的行B,這樣會通路事務表;再試試不同的塊

操作前先檢視下X$BH:

080B51BC         67

接着剛才的實驗,我又通路了不同的塊:

SQL&gt; select * from jj_3 where rowid='AAAMvjAAKAAAAEeAAA';

再次檢視X$BH的結果是:

結果很明顯了,用rowid通路不同的塊,是不會增加TCH值的.也就是說不會有CR塊産生.在晶晶實驗六中,已經證明了在生成CR塊時,oracle可以根據資料塊頭部的ITL槽中的UBA,找到存放資料塊復原資訊的復原塊和復原記錄,通過這個UBA就可以構造CR塊咯,oracle為什麼還要再去通路事務表呢?這是因為,oracle的送出有時會是延遲送出.oracle并不清除延遲送出所涉及的塊中的事務資訊,如:事務所占ITL槽和行鎖.而把清除事務資訊這個操作放到了以後的塊清除中(塊清除在以後的實驗會詳細講述),oracle這樣做的目的是為加快送出速度.如果一個事務涉及到了過多的塊,單單是送出時清除每個塊中的事務資訊就需要耗費很長時間.這降低了送出速度.有可能使送出成為最易引起争用的操作.當事務送出時,對事務所涉及的塊,不做任何操作,塊将保持事務仍在持續時的資訊.當一個select操作查詢到這個塊時,ITL槽中的送出标志為未送出,但實際上這個事務是已經送出的.就是因為有了延遲送出oracle無法根據ITL槽中的送出标志來判斷一個塊中的事務是否真的送出.他必須根據ITL中的XID

去通路事務表.才能确定此塊中的事務是否真的送出.在生成CR塊前,oracle先要判斷是否真的有必要為此塊生成CR塊.這就要去通路事務表.