Oracle語句優化 個規則詳解 11

2021-04-18 08:49:01 字數 2652 閱讀 5457

45.       需要當心的where子句

某些select 語句中的where子句不使用索引。 這裡有一些例子。

在下面的例子裡, 『!=』 將不使用索引。 記住, 索引只能告訴你什麼存在於表中, 而不能告訴你什麼不存在於表中。

不使用索引:

select account_name

from transaction

where amount !=0;

使用索引:

select account_name

from transaction

where amount >0;

下面的例子中, 『||』是字元連線函式。 就象其他函式那樣, 停用了索引。

不使用索引:

select account_name,amount

from transaction

where account_name||account_type=『amexa』;

使用索引:

select account_name,amount

from transaction

where account_name = 『amex』and account_type=『 a』;

下面的例子中, 『+』是數學函式。 就象其他數學函式那樣, 停用了索引。

不使用索引:

select account_name, amount

from transaction

where amount + 3000 >5000;

使用索引:

select account_name, amount

from transaction

where amount > 2000 ;

下面的例子中,相同的索引列不能互相比較,這將會啟用全表掃瞄。

不使用索引:

select account_name, amount

from transaction

where account_name = nvl(:acc_name,account_name);

使用索引:

select account_name, amount

from transaction

where account_name like nvl(:acc_name,『%』);

譯者按:如果一定要對使用函式的列啟用索引, oracle新的功能: 基於函式的索引(function-based index) 也許是乙個較好的方案。

create index emp_i on emp (upper(ename)); /*建立基於函式的索引*/

select * from emp where upper(ename) = 『blacksnail』; /*將使用索引*/

46.       連線多個掃瞄

如果你對乙個列和一組有限的值進行比較, 優化器可能執行多次掃瞄並對結果進行合併連線。

舉例:select *

from lodging

where manager in (『bill gates』,『ken muller』);

優化器可能將它轉換成以下形式

select *

from lodging

where manager = 『bill gates』or manager = 『ken muller』;

當選擇執行路徑時, 優化器可能對每個條件採用lodging$manager上的索引範圍掃瞄。 返回的rowid用來訪問lodging表的記錄 (通過table access by rowid 的方式)。 最後兩組記錄以連線

(concatenation)的形式被組合成乙個單一的集合。

explain plan :

select statement optimizer=choose

concatenation

table access (by index rowid) of lodging

index (range scan ) of lodging$manager (non-unique)

table access (by index rowid) of lodging

index (range scan ) of lodging$manager (non-unique)

譯者按:本節和第37節似乎有矛盾之處。

47.       cbo下使用更具選擇性的索引

基於成本的優化器(cbo, cost-based optimizer)對索引的選擇性進行判斷來決定索引的使用是否能提高效率。

如果索引有很高的選擇性, 那就是說對於每個不重複的索引鍵值,只對應數量很少的記錄。     比如, 表中共有100條記錄而其中有80個不重複的索引鍵值。 這個索引的選擇性就是80/100 = 0.8 . 選擇性越高, 通過索引鍵值檢索出的記錄就越少。

如果索引的選擇性很低, 檢索資料就需要大量的索引範圍查詢操作和rowid 訪問表的操作。 也許會比全表掃瞄的效率更低。

譯者按: 下列經驗請參閱:

a.       如果檢索資料量超過30%的表中記錄數。使用索引將沒有顯著的效率提高。

b.       在特定情況下, 使用索引也許會比全表掃瞄慢, 但這是同乙個數量級上的區別。 而通常情況下,使用索引比全表掃瞄要快幾倍乃至幾千倍!

Oracle語句優化 個規則詳解

1.選用適合的oracle優化器 2.訪問table的方式oracle 採用兩種訪問表中記錄的方式 3.共享sql語句 4.選擇最有效率的表名順序 只在基於規則的優化器中有效 5.where子句中的連線順序。6.select子句中避免使用 7.減少訪問資料庫的次數 8.使用decode函式來減少處理...

Oracle語句優化 個規則詳解 10

42.使用提示 hints 對於表的訪問,可以使用兩種hints.full 和 rowid full hint 告訴oracle使用全表掃瞄的方式訪問指定表。例如 select full emp from emp where empno 7893 rowid hint 告訴oracle使用table...

oracle語句優化規則二

oracle採用自下而上的順序解析where子句,根據這個原理,表之間的連線必須寫在其他where條件之前,那些可以過濾掉最大數量記錄的條件必須寫在where子句的末尾。1.where子句中的連線順序。oracle採用自下而上的順序解析where子句,根據這個原理,表之間的連線必須寫在其他where...