2014-09-04 2 views
1

Существует example использования функций на основе индексов в документации Концепции Oracle 11G:Какую причину использовать индексирование определенных строк в таблице?

индекс функции на основе также полезен для индексации только определенные строки в таблице. Например, столбец cust_valid в таблице sh.customers имеет значение I или A в качестве значения. Чтобы индексировать только строки A, вы можете написать функцию, которая возвращает нулевое значение для любых других строк , чем строки A.

Я могу представить только этот прецедент: уменьшающий размер индекса, исключая некоторые строки по условию. Существуют ли другие варианты использования, когда эта возможность полезна?

+1

Например, столбец COMPLETED, который равен Y для 99,999% строк, и вы хотите запросить только тех, у кого есть COMPLETED! = Y. Тогда такой небольшой индекс в NULLIF (COMPLETED, 'Y') будет делать запросы на WHERE NULLIF (ЗАВЕРШЕН, «Y») НЕ НУЛЛ или ГДЕ NULLIF (ЗАВЕРШЕН, 'Y') = 'N', способный быстро выполнить FAST FULL сканирование индекса. –

ответ

1

Давайте посмотрим на функции на основе индексов:

SQL> create table tab1 as select object_name from all_objects; 

Table created. 

SQL> exec dbms_stats.gather_table_stats(user, 'TAB1'); 

PL/SQL procedure successfully completed. 

SQL> set autotrace traceonly 
SQL> select count(*) from tab1 where lower(object_name) = 'all_tables'; 


Execution Plan 
---------------------------------------------------------- 
Plan hash value: 1117438016 

--------------------------------------------------------------------------- 
| Id | Operation   | Name | Rows | Bytes | Cost (%CPU)| Time  | 
--------------------------------------------------------------------------- 
| 0 | SELECT STATEMENT |  |  1 | 19 | 18 (0)| 00:00:01 | 
| 1 | SORT AGGREGATE |  |  1 | 19 |   |   | 
|* 2 | TABLE ACCESS FULL| TAB1 | 181 | 3439 | 18 (0)| 00:00:01 | 
--------------------------------------------------------------------------- 

Predicate Information (identified by operation id): 
--------------------------------------------------- 

    2 - filter(LOWER("OBJECT_NAME")='all_tables') 


Statistics 
---------------------------------------------------------- 
      1 recursive calls 
      0 db block gets 
     63 consistent gets 
      ... 

Как вы знаете, все объекты имеют уникальные имена, но оракул должен анализировать все 181 строк и выполняет 63 последовательно получает (физический или логический блок читает)

Давайте создадим функцию на основе индекса:

SQL> create index tab1_obj_name_idx on tab1(lower(object_name)); 

Index created. 

SQL> select count(*) from tab1 where lower(object_name) = 'all_tables'; 

Execution Plan 
---------------------------------------------------------- 
Plan hash value: 707634933 

--------------------------------------------------------------------------------------- 
| Id | Operation   | Name    | Rows | Bytes | Cost (%CPU)| Time  | 
--------------------------------------------------------------------------------------- 
| 0 | SELECT STATEMENT |     |  1 | 17 |  1 (0)| 00:00:01 | 
| 1 | SORT AGGREGATE |     |  1 | 17 |   |   | 
|* 2 | INDEX RANGE SCAN| TAB1_OBJ_NAME_IDX | 181 | 3077 |  1 (0)| 00:00:01 | 
--------------------------------------------------------------------------------------- 

Predicate Information (identified by operation id): 
--------------------------------------------------- 

    2 - access(LOWER("OBJECT_NAME")='all_tables') 


Statistics 
---------------------------------------------------------- 
      1 recursive calls 
      0 db block gets 
      2 consistent gets 
      ... 

Как вы можете увидеть сокращение расходов вниз (от 18 до 1) резко и есть только 2 состоят ent получает.

Таким образом, функциональные индексы могут значительно повысить производительность вашего приложения.

Смежные вопросы