Сравнение версий

Ключ

  • Эта строка добавлена.
  • Эта строка удалена.
  • Изменено форматирование.

...

Блок кода
sql
sql
analyze table t compute statistics for columns s size 254;
select endpoint_number, endpoint_value, substr(endpoint_actual_value, 1, 30) 
   from user_tab_histograms where table_name = 'T' and column_name = 'S';

analyze table t compute statistics for columns s size 8;

select endpoint_number, endpoint_value, substr(endpoint_actual_value, 1, 30) 
   from user_tab_histograms where table_name = 'T' and column_name = 'S';

analyze table t compute statistics for columns s size 254;

select endpoint_number, endpoint_value, substr(endpoint_actual_value, 1, 30) 
   from user_tab_histograms where table_name = 'T' and column_name = 'S';

select s, count(*) from t group by s;

Пути доступа к данным

Подготовка данных.

Блок кода
sql
sql

-- создание объектов
drop table h;

-- create table h(p number constraint pk primary key, s varchar2(100) null, n number null, nu number null constraint un unique);
create table h(p number, s varchar2(100) null, n number null, nu number null);
Полное сканирование таблицы. Преимущества, недостатки.

Для выборки данных производится перебор всех строк таблицы, возвращаются строки подходящие под условия запроса. Может быть эффективнее использования индекса в случаях когда необходимо выбрать >25-30% записей в таблице. Возникает проблема High Water Mark.

Блок кода
sql
sql

-- полное сканирование таблицы. high water mark

insert into h select -rownum, object_name, object_id, object_id from all_objects where rownum < 100;

insert into h select rownum, object_name, object_id, object_id from all_objects;

select * from h where p < 0;

analyze table h compute statistics for table for all columns for all indexes;
select num_rows, blocks, empty_blocks from user_tables where table_name = 'H';

delete from h where p > 0;
Классические индексы.

Индексы на основе В*-дерева наиболее широко используемый тип индексной структуры в базе данных. По реализации они подобны двоичному дереву поиска. Цель их создания — минимизировать время поиска данных сервером Oracle. При наличии индекса по числовому столбцу, структура индекса может выглядеть так:
Image Added

Блоки самого нижнего уровня в индексе, которые называют листовыми вершинами, содержат все проиндексированные ключи и идентификаторы строк (rid на схеме), ссылающиеся на соответствующие строки. Промежуточные блоки над листовыми вершинами называют блоками ветвления. Они используются для переходов по структуре. Например, если необходимо найти в индексе значение 42, надо начать с вершины дерева и двигаться вправо. При проверке этого блока оказывается, что необходимо перейти к блоку в диапазоне "от 40 до 50". Этот блок оказывается листовым и ссылается на строки, содержащие число 42. Интересно отметить, что листовые блоки фактически образуют двухсвязный список. Как только найдено "начало" среди листовых вершин, т.е. первое значение, очень легко просматривать значения по порядку (это называют также просмотром диапазона по индексу, index range scan). Проходить по структуре индекса больше не нужно; мы просто переходим по листовым вершинам. Это существенно упрощает поиск строк но условиям следующего вида:

where x between 20 and 30

Блок кода
sql
sql

-- индексы
-- структура индекса, rowid
truncate table h;
insert into h select rownum, object_name, object_id, object_id from all_objects where rownum < 10;
commit;

select rowid, p from h;

select * from h where rowid = 'AAAN95AAEAAAAfHAAA';

declare
	r_t number;
	o_n number;
	f_n number;
	b_n number;
	r_n number;
	r rowid;
begin
	select rowid into r from h where rownum < 2;

	dbms_rowid.rowid_info(r, r_t, o_n, f_n, b_n, r_n);

	dbms_output.put_line('rowid type    = ' || r_t);
	dbms_output.put_line('object number = ' || o_n);
	dbms_output.put_line('file number   = ' || f_n);
	dbms_output.put_line('block number  = ' || b_n);
	dbms_output.put_line('row number    = ' || r_n);
end;

select * from user_objects where object_name = 'H';
select * from user_tables where table_name = 'H';
select * from dba_data_files;

-- создание индексов
truncate table h;

insert into h select rownum, object_name, object_id, object_id from all_objects;

commit;

create index ind_s on h(s);
select * from user_indexes where table_name = 'H';
drop index ind_s;
select * from user_indexes where table_name = 'H';

create index ind_s_1 on h(s desc);
create unique index ind_n on h(n);

select index_name, index_type, table_name, status, funcidx_status from user_indexes where table_name = 'H';

-- информация по таблицам и индексам
select * from user_tables;
select * from user_tab_columns;
select * from user_constraints;
select * from user_cons_columns;
select * from user_indexes;
select * from user_ind_columns;