Oracle 執行計劃的檢視方式
阿新 • • 發佈:2018-12-08
訪問資料的方法:一、訪問表的方法:1.全表掃描,2.ROWID掃描
二、訪問索引的方法:1.索引唯一性掃描,2.索引範圍掃描,3.索引全掃描,4.索引快速全掃描,5.索引跳躍式掃描
表連線:1.排序合併連線,2.巢狀迴圈連線,3.雜湊連線,4.反連線,5.半連線,6.星型連線(多用於資料倉庫,是一種單個事實表和多個維度表之間的連線,事實表和維度表之間是基於事實表的外來鍵列和對應維度表的主鍵之間的連線)
執行計劃:
方式一、explain plan
SQL> explain plan for select empno,ename,dname from scott.emp,scott.dept where emp.deptno = dept.deptno;
Explained
SQL> select * from table(dbms_xplan.display);
方式二、DBMS_XPLAN 包
針對不同的場景,可以選擇四種不同的方法中的一種:
1.select * from table(dbms_xplan.display)
這需要和explain plan 配合使用,上面已經展示
2.select * from table(dbms_xplan.display_cursor(null,null,'advanced'))
用於在sqlplus中檢視剛剛執行過的sql的執行計劃,第三個引數還可為all,只是第三個引數是advanced結果會更詳細
3.select * from table(dbms_xplan.display_cursor('sql_id/hash_value',child_cursor_number,'advanced'))
用於檢視指定sql的執行計劃,sql_id/hash_value和child_cursor_number可從v$sql檢視中找到:
select sql_text,sql_id,hash_value,child_number from v$sql where sql_text like 'SQL';
只要目標SQL的執行計劃所在的Child Cursor還麼有被age out出Share Pool,就可以使用此方法。
4.select * from table(dbms_xplan.display_awr('sql_id'))
用於檢視指定sql的所有歷史執行計劃。 方法2和3能夠顯示目標SQL執行計劃的前提條件是該SQL還在Share Pool中,如果已經被age out出Share Pool,那麼只要該SQL的執行計劃被Oracle採集到AWR Repository中,我們就可以使用方法4來檢視該SQL的所有執行計劃。
select sql_text,sql_id,version_count,executions from v$sqlarea where sql_text like 'SQL';
version_count可以看出該SQL有幾個Child Cursor。
和方法2和3相比,有個不好的地方是看不到執行步驟對應的謂詞條件
方法三、AUTOTRACE開關
在sqlplus中將AUTOTRACE開關開啟也能得到目標sql的執行計劃,還能額外觀察到目標SQL執行所消耗的物理讀、邏輯讀、產生redo的數量以及排序的數量。
SET AUTOTRACE {OFF|ON|TRACEONLY}
[EXPLAIN]
[STATISTICS]
SESSION預設是SET AUTOTRACE OFF
1.在當前SESSION中執行 SET AUTOTRACE ON 可以在當前session中開啟AUTOTRACE開關,這樣,這個SESSION中隨後執行的所有SQL除了顯示SQL執行結果之外,還會額外顯示SQL所對應的執行計劃和資源消耗情況。
2.在當前SESSION中執行 SET AUTOTRACE TRACEONLY,可以在當前SESSION中只顯示SQL執行計劃和額外消耗,而不顯示結果。
3.在當前SESSION中執行SET AUTOTRACE TRACEONLY EXPLAIN 可以在當前SESSION中只顯示執行計劃(SELECT不會被實際執行,DML語句會被實際執行) 4.在當前SESSION中執行SET AUTOTRACE TRACEONLY STATISTICS 可以在當前SESSION中只顯示資源消耗 方法四、10046事件與tkprof命令 10046事件與上面三種的不同之處在於,所得到的執行計劃中明確顯示了目標SQL實行執行計劃中每一個執行步驟所消耗的邏輯讀、物理讀和花費時間。 < 略 > 除了第四種方法外,前三種的方法得到的執行計劃有可能是不準確的,要判斷執行計劃是否準確,就是看目標SQL是否真正被執行過,真正被實際執行過的SQL得到的執行計劃準確。(此原則不適用於AUTOTRACE開關,因為所有使用AUTOTRACE開關所顯示的執行計劃都有可能是不準確的,即使對應的目標SQL已經被執行過,因為使用SET AUTOTRACE命令所顯示的執行計劃來源都是呼叫explain plan命令) 第一種方法得到的執行計劃,目標SQL是沒有被被實際執行過的,執行計劃可能是不準確的尤其是目標SQL包含繫結變數時。 第二種方法的 2,3,4 得到的執行計劃是準確的,因為此時目標SQL已經被實際執行過。 cuihua檢視真實執行計劃的指令碼用法 9i: @'e:\xxx' sql_id child_cursor_number --適合於9i之前資料庫 printsql: 在資料庫伺服器上執行 topas命令後顯示 SPID為1234的Oracle程序佔用了14%CPU,檢視這程序在做什麼: exec printsql(1234,'SPID') printsql可幫把這個程序正在執行的SQL,該SQL真實的執行計劃以及殺這個Session的語句打印出來 檢視執行計劃順序口訣:先從最開頭一直連續往右看,直到看到最右邊的並列的地方;對於不併列的,靠右的先執行;如果見到並列的,就從上往下看,對於並列的部分,考上的先執行。 cuihua 檢視執行順序的指令碼 xplan包 select * from table(xplan.display_cursor('sql_id',child_number,'advanced'));
3.在當前SESSION中執行SET AUTOTRACE TRACEONLY EXPLAIN 可以在當前SESSION中只顯示執行計劃(SELECT不會被實際執行,DML語句會被實際執行) 4.在當前SESSION中執行SET AUTOTRACE TRACEONLY STATISTICS 可以在當前SESSION中只顯示資源消耗 方法四、10046事件與tkprof命令 10046事件與上面三種的不同之處在於,所得到的執行計劃中明確顯示了目標SQL實行執行計劃中每一個執行步驟所消耗的邏輯讀、物理讀和花費時間。 < 略 > 除了第四種方法外,前三種的方法得到的執行計劃有可能是不準確的,要判斷執行計劃是否準確,就是看目標SQL是否真正被執行過,真正被實際執行過的SQL得到的執行計劃準確。(此原則不適用於AUTOTRACE開關,因為所有使用AUTOTRACE開關所顯示的執行計劃都有可能是不準確的,即使對應的目標SQL已經被執行過,因為使用SET AUTOTRACE命令所顯示的執行計劃來源都是呼叫explain plan命令) 第一種方法得到的執行計劃,目標SQL是沒有被被實際執行過的,執行計劃可能是不準確的尤其是目標SQL包含繫結變數時。 第二種方法的 2,3,4 得到的執行計劃是準確的,因為此時目標SQL已經被實際執行過。 cuihua檢視真實執行計劃的指令碼用法 9i: @'e:\xxx' sql_id child_cursor_number --適合於9i之前資料庫 printsql: 在資料庫伺服器上執行 topas命令後顯示 SPID為1234的Oracle程序佔用了14%CPU,檢視這程序在做什麼: exec printsql(1234,'SPID') printsql可幫把這個程序正在執行的SQL,該SQL真實的執行計劃以及殺這個Session的語句打印出來 檢視執行計劃順序口訣:先從最開頭一直連續往右看,直到看到最右邊的並列的地方;對於不併列的,靠右的先執行;如果見到並列的,就從上往下看,對於並列的部分,考上的先執行。 cuihua 檢視執行順序的指令碼 xplan包 select * from table(xplan.display_cursor('sql_id',child_number,'advanced'));
<wiz_tmp_tag id="wiz-table-range-border" contenteditable="false" style="display: none;">