Здравствуйте. Помогите с запросом и
оптимизацией.
В общем есть две таблицы главная и
подчинённая.
1. Главная - Таблица доставок:
CREATE TABLE DOSTAVKA (
DOSTAVKA_ID INTEGER NOT NULL,
DOSTAVKA_DATE DATE NOT NULL,
PRIMECH VARCHAR(200),
STATUS SMALLINT DEFAULT 0 NOT NULL,
);
2. Подчинённая - Таблица счетов к этим
доставкам.
CREATE TABLE DOSTAVKA_SCHETA (
DOSTAVKA_SCHETA_ID INTEGER NOT NULL,
DOSTAVKA_ID INTEGER,
SCHET VARCHAR(10) NOT NULL,
);
У DOSTAVKA есть поле STATUS которое указывает
подписанна доставка (1) или нет (0),
естествено поле проиндексировано.
Также проиндексированно поле SCHET
(номера доставляемых счетов).
Задача: Показать все подписанные
доставки когда отправляли счёт 111/111.
Для экспериментов с таблицами
использую IBExpert. Версия сервера FB-1.5.3. В
тестовых данных забитых в DOSTAVKA_SCHETA.SCHET
искомый счёт 111/111 повторяется в двух
строках.
В DOSTAVKA забито 10 строк из них 8 имеют STATUS
= 1.
Сосбвенно делаю запрос:
SELECT DOSTAVKA.DOSTAVKA_ID, DOSTAVKA.DOSTAVKA_DATE,
DOSTAVKA.STATUS, DOSTAVKA_SCHETA.SCHET
FROM DOSTAVKA
INNER JOIN DOSTAVKA_SCHETA ON
(DOSTAVKA.DOSTAVKA_ID = DOSTAVKA_SCHETA.DOSTAVKA_ID)
WHERE
DOSTAVKA_SCHETA.SCHET = '111/111'
AND
DOSTAVKA.STATUS = 1
ORDER BY DOSTAVKA.DOSTAVKA_DATE, DOSTAVKA.DOSTAVKA_ID
Получаю верный результат:
DOSTAVKA_ID DOSTAVKA_DATE STATUS SCHET
129 08.02.2006 1 111/111
132 08.02.2006 1 111/111
План:
PLAN SORT (JOIN (DOSTAVKA INDEX (DOSTAVKA_IDX2),DOSTAVKA_SCHETA INDEX
(DOSTAVKA_SCHETA_IDX1,FK_DOSTAVKA_SCHETA_1)))
Лезу в анализ производительности,
удивляюсь:
Индексные чтения:
DOSTAVKA_SCHETA - 2 ... как и ожидалось!
DOSTAVKA - 8 !!!!!
Получается что что бы сформировать
результат из 2-х строк, запрос молотит
все индексы STATUS со значением 1 ? ... а
если записей 1000000 и из них 900000 со STATUS = 1
то FB будет перебирать все 900000 индексов
? Белиберда какая то. Народ помогите
переписать запрос так что бы индексных
чтений было не больше 2. Или это грабли
планировщика ?!!! HELP!
Описание индексов:
DOSTAVKA:
ALTER TABLE DOSTAVKA ADD CONSTRAINT PK_DOSTAVKA PRIMARY KEY
(DOSTAVKA_ID);
CREATE INDEX DOSTAVKA_IDX1 ON DOSTAVKA (DOSTAVKA_DATE);
CREATE INDEX DOSTAVKA_IDX2 ON DOSTAVKA (STATUS);
DOSTAVKA_SCHETA:
ALTER TABLE DOSTAVKA_SCHETA ADD CONSTRAINT PK_DOSTAVKA_SCHETA PRIMARY
KEY (DOSTAVKA_SCHETA_ID);
ALTER TABLE DOSTAVKA_SCHETA ADD CONSTRAINT FK_DOSTAVKA_SCHETA_1 FOREIGN
KEY (DOSTAVKA_ID) REFERENCES DOSTAVKA (DOSTAVKA_ID) ON DELETE CASCADE
ON UPDATE CASCADE;
CREATE INDEX DOSTAVKA_SCHETA_IDX1 ON DOSTAVKA_SCHETA (SCHET);