2015-06-16 59 views
0
CONNECT alll/all 

SELECT /*+ FIRST_ROWS(25) */ employee_id, department_id 
    FROM hr.employees 
    WHERE department_id > 50; 

Execution Plan 
    Plan hash value: 2056577954 


| Id | Operation     | Name    | Rows | Bytes | 
| 0 | SELECT STATEMENT   |     | 25 | 200 
| 1 | TABLE ACCESS BY INDEX ROWID| EMPLOYEES   | 25 | 200 
|* 2 | INDEX RANGE SCAN   | **EMP_DEPARTMENT_IX** |  |  


SQL> select * from user_indexes where index_name = 'EMP_DEPARTMENT_IX'; 

no rows selected 

注意不存在索引:有相同名稱的Employees表的DEPARTMENT列在一些其他模式的索引。當該索引被刪除時,將執行EMPLOYEES上的全表掃描。優化使用在當前模式

優化器可以使用來自其他架構的其他索引嗎?

回答

2

你作爲連接用戶ALLL,但你在HR模式查詢表:

SELECT /*+ FIRST_ROWS(25) */ employee_id, department_id 
    FROM hr.employees 
    WHERE department_id > 50; 

你在問題中強調其他模式,但似乎都忽略了這個表你重新查詢也在另一個模式中。僱員表也不會出現在user_tables之中。

正在使用的索引與該表相關聯,因此它可能位於相同的HR模式中。你可以在all_indexesdba_indexes;即使你看不到它,優化器也會使用它。它不必與表格在同一個模式中,儘管它通常是這樣;在這些視圖中您可能會注意到單獨的所有者和表所有者列。

如果只能在訪問別人的表中的表時使用自己的模式中的索引,那麼模式模型會崩潰。每個用戶都必須創建自己的索引副本,這是站不住腳的。

你甚至不一定能夠看到表 - 如果你查詢隱藏你的基礎表的視圖(所以你只在視圖上選擇priv)索引仍然會用在背景。並且,如果表的同義詞存在,或者您更改了默認模式,則可能並不總是顯式使用模式前綴。

0

嘗試尋找在SYS.INDEXES

select * from SYS.INDEXES where IXNAME = 'EMP_DEPARTMENT_IX' 

聽起來像是你不在索引的所有者,因爲你已經注意到。只要您的用戶可以訪問表數據,那麼索引應該被優化器使用。

+0

Oracle的等價物將是'all_indexes'或'dba_indexes',並查詢'index_name'。 –