powered by simpleCommunicator - 2.0.61     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Firebird, InterBase [игнор отключен] [закрыт для гостей] / alter index INactive для индекса depth=13 делается ~80 сек. Why ?
4 сообщений из 4, страница 1 из 1
alter index INactive для индекса depth=13 делается ~80 сек. Why ?
    #38820115
Таблоид
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
hi all

Имеется вот такая базейка (page_size = 16384) с одной табличкой и несколькими "кошмарными" индексами:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
set bail on;
commit;
set transaction no wait;
recreate sequence g;
recreate table ts(id int not null, s varchar(3250));
commit;
set transaction no wait;
set echo on;
create index ts_sub_full on ts(s);
create index ts_sub_0250 on ts computed by( substring(s from 1 for 250) );
create index ts_sub_0500 on ts computed by( substring(s from 1 for 500) );
create index ts_sub_0750 on ts computed by( substring(s from 1 for 750) );
create index ts_sub_1000 on ts computed by( substring(s from 1 for 1000) );
create index ts_sub_1250 on ts computed by( substring(s from 1 for 1250) );
create index ts_sub_1500 on ts computed by( substring(s from 1 for 1500) );
create index ts_sub_1750 on ts computed by( substring(s from 1 for 1750) );
create index ts_sub_2000 on ts computed by( substring(s from 1 for 2000) );
create index ts_sub_2250 on ts computed by( substring(s from 1 for 2250) );
create index ts_sub_2500 on ts computed by( substring(s from 1 for 2500) );
create index ts_sub_2750 on ts computed by( substring(s from 1 for 2750) );
create index ts_sub_3000 on ts computed by( substring(s from 1 for 3000) );
set echo off;
commit;
--exit;
select current_connection,current_timestamp as dts_start_ins from rdb$database;

set stat on;
set echo on;
insert into ts
select gen_id(g,1) i, rpad('', 3250, uuid_to_char(gen_uuid())) s
from rdb$types, rdb$types,(select 1 i from rdb$types rows 10) -- ~645160
rows 200000;
set echo off;
set stat off;

select current_connection,current_timestamp as dts_finish_ins from rdb$database;

set stat on;
set echo on;
commit;
set echo off;
set stat off;

select current_connection,current_timestamp as dts_done_commit from rdb$database;

alter table ts add constraint ts_pk primary key(id) using index ts_pk;
commit;
exit;
gstat -r по ней будет показывать для индексов с длинными ключами глубины 10...13.

Если после её создания приконнектиться единственным аттачем (без указания '-n') и сделать вот это:
Код: plaintext
SQL> commit; set transaction no wait; set stat on; alter index ts_sub_full  in active; commit; set stat off;
- то получим:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
Current memory = 8893455328
Delta memory = 362816
Max memory = 8893568280
 Elapsed time= 80.402 sec 
Cpu = 0.000 sec
Buffers = 524288
Reads = 66697
Writes = 16
Fetches = 134045
Current memory = 8893449560
Delta memory = -11320
Max memory = 8893568280
Elapsed time= 0.001 sec
Cpu = 0.000 sec
Buffers = 524288
Reads = 0
Writes = 2
Fetches = 2

Трейс покажет, что время:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
2014-11-29T00:40:41.6740 (8579:0x7f1b16ead430) COMMIT_TRANSACTION
        /var/db/fb30/tmpstr.fdb (ATT_109, SYSDBA:NONE, NONE, TCPv4:127.0.0.1)
        /opt/fb30trnk/bin/isql:30225
                (TRA_144, READ_COMMITTED | NO_REC_VERSION |  WAIT  | READ_WRITE)
  80372 ms, 66681 read(s), 6 write(s), 133443 fetch(es), 66671 mark(s)

Table                             Natural     Index    Update    Insert    Delete
*********************************************************************************
RDB$INDICES                                       1         1
- было потрачено на коммит DDL-транзакции, которая стартовала автоматом при вводе alter index ... inactive.

Если теперь снова сделать коннект (по-прежнему единственный) и ввести:
Код: plaintext
SQL> commit; set transaction no wait; set stat on; alter index ts_sub_full  active ; commit; set stat off;
- а затем, НЕ выходя из ISQL'я, снова деактивировать индекс:
Код: plaintext
SQL> commit; set transaction no wait; set stat on; alter index ts_sub_full  INactive ; commit; set stat off;
- то это уже выполнится мгновенно:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
2014-11-29T00:48:53.0550 (8579:0x7f1b16eb0188) COMMIT_TRANSACTION
        /var/db/fb30/tmpstr.fdb (ATT_112, SYSDBA:NONE, NONE, TCPv4:127.0.0.1)
        /opt/fb30trnk/bin/isql:30365
                (TRA_156, READ_COMMITTED | NO_REC_VERSION | WAIT | READ_WRITE)
     66 ms, 6 write(s), 133364 fetch(es), 66671 mark(s)

Table                             Natural     Index    Update    Insert    Delete
*********************************************************************************
RDB$INDICES                                       1         1

Как только делаем переконнект, так сразу получаем затык по времени для INactive.

Отчего это ?
...
Рейтинг: 0 / 0
alter index INactive для индекса depth=13 делается ~80 сек. Why ?
    #38820271
hvlad
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Таблоид,

при удалении (де-активации) индекса движок должен пометить все его страницы, как свободные.
Для этого их нужно найти. Для этого нужно обойти всё дерево, кроме листьев.

В первом случае у тебя коммит читает 66681 страницу. Это значит, что индекса нет в кеше и читает его именно коммит. Отсюда задержка 80 сек.

Во втором случае ты в одном и том же коннекте сначала создал индекс (тем самым поместил его в кеш), а потом удаляешь (деактивируешь). Поэтому коммит ничего не читает и выполняется быстро.
...
Рейтинг: 0 / 0
alter index INactive для индекса depth=13 делается ~80 сек. Why ?
    #38820283
Таблоид
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
hvladпри удалении (де-активации) индекса движок должен пометить все его страницы, как свободные.
Для этого их нужно найти. Для этого нужно обойти всё дерево, кроме листьев.

В первом случае у тебя коммит читает 66681 страницу. Это значит, что индекса нет в кеше и читает его именно коммит. Отсюда задержка 80 сек."век живу - тупкой помру": почему-то считал, что alter index inactive не только держит индекс в словаре БД, но еще и не занимается пометкой его страниц как свободных (полагал, что это всё только drop index делает).

PS. А почему ты говоришь, что "обойти надо всё дерево, КРОМЕ листьев" ? Страницы листового уровня - они что, "не участвуют в самодеятельности" ?
...
Рейтинг: 0 / 0
alter index INactive для индекса depth=13 делается ~80 сек. Why ?
    #38820292
hvlad
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ТаблоидА почему ты говоришь, что "обойти надо всё дерево, КРОМЕ листьев" ? Страницы листового уровня - они что, "не участвуют в самодеятельности" ?Потому, что номера страниц последнего (листового) уровня известны на предпоследнем уровне :)
...
Рейтинг: 0 / 0
4 сообщений из 4, страница 1 из 1
Форумы / Firebird, InterBase [игнор отключен] [закрыт для гостей] / alter index INactive для индекса depth=13 делается ~80 сек. Why ?
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]