![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Результаты выполнение ХП с индексами и без [FB 1.5]
yaral © (2006-07-24 14:32:00)У меня имеется ХП которая делает выборку по 1-й таблице. Когда я ее делал индексов в этой таблице не было, и она правильно работала. Но как только для увиличение быстродействия я добавил индексы, ХП стала возращать не правильные результаты.
От чего подобное может произойти? Может версия сервера с багами? Использую FB 1.5.0.4306.
Desdechado (2006-07-25 13:33:00) [1]Для интереса, покажи 2 полученных набора данных в правильном и неправильном варианте.
atruhin (2006-07-25 13:30:00) [2]Опять то же самое.
FOR SELECT CONTREE_ID, PARENT_ID, OBJ_ID, RTYPE_ID, LNAME, CODE, ORDERINT, STATE FROM CONTREE
WHERE PARENT_ID=:CONTREE_ID AND (STATE=:ISTATE1 OR STATE=:ISTATE2)
ORDER BY ORDERINT
INTO : CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO BEGIN
SUSPEND;
IF (NOT EXISTS (SELECT * FROM CONTREE
WHERE PARENT_ID=: CONTREE_IDAND (STATE=:ISTATE1 OR STATE=:ISTATE2)
)) THEN
BEGIN
VCONTREE_ID = :CONTREE_ID;
VNOREC_ID = :VNOREC_ID - 1;
FOR SELECT :VNOREC_ID, :VCONTREE_ID, :OBJ_ID, 7, '', '<...>', 1, :STATE FROM ZX
INTO : CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO SUSPEND;
END
ELSE BEGIN
FOR SELECT CONTREE_ID, PARENT_ID, OBJ_ID, RTYPE_ID, LNAME, CODE, ORDERINT, STATE FROM CONTREE
WHERE PARENT_ID=: CONTREE_IDAND (STATE=:ISTATE1 OR STATE=:ISTATE2)
ORDER BY FMAIN DESC, ORDERINT
INTO : CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO SUSPEND;
END
Т.е. ты то присваеваешь, не понятно что потом используеш.
yaral (2006-07-25 12:53:00) [3]> atruhin © (25.07.06 12:27) [17]
Ага действительно странно, что это я так, но я думаю это к делу не относиться т.к. под условиеWHERE PARENT_ID=:CONTREE_IDc CONTREE_ID<0 все равно ни одна запись не подойдет.
Но исправил на такой вариант, все тоже самое.
CREATE PROCEDURE BUILD_CONTREE(
IOBJ_ID INTEGER,
ISTATE1 INTEGER,
ISTATE2 INTEGER)
RETURNS (
CONTREE_ID INTEGER,
PARENT_ID INTEGER,
OBJ_ID INTEGER,
RTYPE_ID INTEGER,
LNAME VARCHAR(250),
CODE VARCHAR(5),
ORDERINT INTEGER,
STATE INTEGER)
AS
DECLARE VARIABLE VNOREC_ID INTEGER;
DECLARE VARIABLE VCONTREE_ID INTEGER;
DECLARE VARIABLE VRTYPE_ID INTEGER;
BEGIN
VNOREC_ID=0;
FOR SELECT CONTREE_ID, PARENT_ID, OBJ_ID, RTYPE_ID, LNAME, CODE, ORDERINT, STATE FROM CONTREE
WHERE OBJ_ID=:IOBJ_ID AND (RTYPE_ID=1 OR RTYPE_ID=2 OR RTYPE_ID=3) AND STATE=1
ORDER BY ORDERINT
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO BEGIN
SUSPEND;
VCONTREE_ID = :CONTREE_ID;
VRTYPE_ID = :RTYPE_ID + 3;
IF (NOT EXISTS (SELECT * FROM CONTREE
WHERE PARENT_ID=:CONTREE_ID AND (STATE=:ISTATE1 OR STATE=:ISTATE2)
)) THEN
BEGIN
VNOREC_ID = :VNOREC_ID - 1;
FOR SELECT :VNOREC_ID, :VCONTREE_ID, :OBJ_ID, :VRTYPE_ID, '', '<...>', 1, :STATE FROM ZX
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO SUSPEND;
END
ELSE BEGIN
FOR SELECT CONTREE_ID, PARENT_ID, OBJ_ID, RTYPE_ID, LNAME, CODE, ORDERINT, STATE FROM CONTREE
WHERE PARENT_ID=:CONTREE_ID AND (STATE=:ISTATE1 OR STATE=:ISTATE2)
ORDER BY ORDERINT
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO BEGIN
SUSPEND;
IF (NOT EXISTS (SELECT * FROM CONTREE
WHERE PARENT_ID=:CONTREE_ID AND (STATE=:ISTATE1 OR STATE=:ISTATE2)
)) THEN
BEGIN
VCONTREE_ID = :CONTREE_ID;
VNOREC_ID = :VNOREC_ID - 1;
FOR SELECT :VNOREC_ID, :VCONTREE_ID, :OBJ_ID, 7, '', '<...>', 1, :STATE FROM ZX
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO SUSPEND;
END
ELSE BEGIN
FOR SELECT CONTREE_ID, PARENT_ID, OBJ_ID, RTYPE_ID, LNAME, CODE, ORDERINT, STATE FROM CONTREE
WHERE PARENT_ID=:CONTREE_ID AND (STATE=:ISTATE1 OR STATE=:ISTATE2)
ORDER BY FMAIN DESC, ORDERINT
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO SUSPEND;
END
END
END
END
END
atruhin (2006-07-25 12:27:00) [4]Здесь ты присваеваешь значение VNOREC_ID - 1
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
Следом за этим ты
WHERE PARENT_ID=:CONTREE_ID
Может я не правильно понял логику, но вроде в ней должно быть значение из внешнего цикла. Далее если в if exist ты убедился что записей нет, зачем ты следом делаешь запрос с такими же параметрами.
yaral (2006-07-25 12:19:00) [5]CONTREE_ID - выходным параметром? Да вроде все нормально, как же не присваевая ему ничего запихнуть его в выходной НД?
atruhin (2006-07-25 12:13:00) [6]Разберись с переменной CONTREE_ID, ты в if присвееваешь ей значение, далее опять используешь и т.д.
yaral (2006-07-25 12:00:00) [7]На выходе получается дерево, с тремя уровнями:
1 - Типы групп (пользователи, функции, зоны), их всегда три.
2 - Сами группы
3 - События
Если в типе групп, нет не одного узла то зозращается пустая запись м именем <...> и отрицательным ид. Также с событиями если их нет.
Так вот, в неправильном варианте, т.е. с индексом, возвращается только первая группа в Типе, а события в ней в полном объеме присутствуют. Т.е. в таблице то они все есть, никуда не делись, я только индекс создал по полю.
Тут же запускаю в режиме трассировки в IB Expert и все записи как и положено вижу. Индекс удаляю, и опять все записи получаю. И на другой машине запускал... тоже самое.
Johnmen (2006-07-25 11:49:00) [8]Хотелось бы уточнить, что значит "дает не верные результаты"? В чём их "неверность"?
yaral (2006-07-25 11:27:00) [9]> atruhin © (25.07.06 10:38) [11]
Процедура:
CREATE PROCEDURE BUILD_CONTREE(
IOBJ_ID INTEGER,
ISTATE1 INTEGER,
ISTATE2 INTEGER)
RETURNS (
CONTREE_ID INTEGER,
PARENT_ID INTEGER,
OBJ_ID INTEGER,
RTYPE_ID INTEGER,
LNAME VARCHAR(250),
CODE VARCHAR(5),
ORDERINT INTEGER,
STATE INTEGER)
AS
DECLARE VARIABLE VNOREC_ID INTEGER;
DECLARE VARIABLE VCONTREE_ID INTEGER;
DECLARE VARIABLE VRTYPE_ID INTEGER;
BEGIN
VNOREC_ID=0;
FOR SELECT CONTREE_ID, PARENT_ID, OBJ_ID, RTYPE_ID, LNAME, CODE, ORDERINT, STATE FROM CONTREE
WHERE OBJ_ID=:IOBJ_ID AND (RTYPE_ID=1 OR RTYPE_ID=2 OR RTYPE_ID=3) AND STATE=1
ORDER BY ORDERINT
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO BEGIN
SUSPEND;
VCONTREE_ID = :CONTREE_ID;
VRTYPE_ID = :RTYPE_ID + 3;
IF (NOT EXISTS (SELECT * FROM CONTREE
WHERE PARENT_ID=:CONTREE_ID AND (STATE=:ISTATE1 OR STATE=:ISTATE2)
)) THEN
BEGIN
VNOREC_ID = :VNOREC_ID - 1;
FOR SELECT :VNOREC_ID, :VCONTREE_ID, :OBJ_ID, :VRTYPE_ID, '', '<...>', 1, :STATE FROM ZX
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO SUSPEND;
END
FOR SELECT CONTREE_ID, PARENT_ID, OBJ_ID, RTYPE_ID, LNAME, CODE, ORDERINT, STATE FROM CONTREE
WHERE PARENT_ID=:CONTREE_ID AND (STATE=:ISTATE1 OR STATE=:ISTATE2)
ORDER BY ORDERINT
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO BEGIN
SUSPEND;
IF (NOT EXISTS (SELECT * FROM CONTREE
WHERE PARENT_ID=:CONTREE_ID AND (STATE=:ISTATE1 OR STATE=:ISTATE2)
)) THEN
BEGIN
VCONTREE_ID = :CONTREE_ID;
VNOREC_ID = :VNOREC_ID - 1;
FOR SELECT :VNOREC_ID, :VCONTREE_ID, :OBJ_ID, 7, '', '<...>', 1, :STATE FROM ZX
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO SUSPEND;
END
FOR SELECT CONTREE_ID, PARENT_ID, OBJ_ID, RTYPE_ID, LNAME, CODE, ORDERINT, STATE FROM CONTREE
WHERE PARENT_ID=:CONTREE_ID AND (STATE=:ISTATE1 OR STATE=:ISTATE2)
ORDER BY FMAIN DESC, ORDERINT
INTO :CONTREE_ID, :PARENT_ID, :OBJ_ID, :RTYPE_ID, :LNAME, :CODE, :ORDERINT, :STATE
DO SUSPEND;
END
END
END
Вызов:
SELECT * FROM BUILD_CONTREE(381, 1, 1)
Без индекса по полю ORDERINT:
План
PLAN (CONTREE INDEX (CONTREE_IDX1))(ZX NATURAL)(CONTREE INDEX (CONTREE_IDX1))(ZX NATURAL)SORT ((CONTREE INDEX (CONTREE_IDX1)))SORT ((CONTREE INDEX (CONTREE_IDX1)))SORT ((CONTREE INDEX (CONTREE_IDX2,CONTREE_IDX3,CONTREE_IDX3,CONTREE_IDX3)))
Адаптированный план
PLAN (CONTREE INDEX (CONTREE_IDX1))(ZX NATURAL)(CONTREE INDEX (CONTREE_IDX1))(ZX NATURAL)SORT ((CONTREE INDEX (CONTREE_IDX1)))SORT ((CONTREE INDEX (CONTREE_IDX1)))SORT ((CONTREE INDEX (CONTREE_IDX2,CONTREE_IDX3,CONTREE_IDX3,CONTREE_IDX3)))
------ Performance info ------
Prepare time = 0ms
Execute time = 100ms
Avg fetch time = 5,88 ms
Current memory = 1 424 752
Max memory = 27 333 076
Memory buffers = 2 048
Reads from disk to cache = 22
Writes from cache to disk = 2
Fetches from cache = 231
С индексом по полю ORDERINT (дает не верные результаты):
План
PLAN (CONTREE INDEX (CONTREE_IDX1))(ZX NATURAL)(CONTREE INDEX (CONTREE_IDX1))(ZX NATURAL)SORT ((CONTREE INDEX (CONTREE_IDX1)))(CONTREE ORDER CONTREE_IDX5)(CONTREE ORDER CONTREE_IDX5)
Адаптированный план
PLAN (CONTREE INDEX (CONTREE_IDX1))(ZX NATURAL)(CONTREE INDEX (CONTREE_IDX1))(ZX NATURAL)SORT ((CONTREE INDEX (CONTREE_IDX1)))(CONTREE ORDER CONTREE_IDX5)(CONTREE ORDER CONTREE_IDX5)
------ Performance info ------
Prepare time = 0ms
Execute time = 50ms
Avg fetch time = 3,85 ms
Current memory = 2 204 040
Max memory = 27 333 076
Memory buffers = 2 048
Reads from disk to cache = 0
Writes from cache to disk = 2
Fetches from cache = 833
atruhin (2006-07-25 10:38:00) [10]> Причем тут кофе?
Намек чтобы ты процедуру выложил?
atruhin (2006-07-25 10:37:00) [11]> Т.е. Это глюк сервера БД надо пологать?
Это глюк процедуры
Johnmen (2006-07-25 09:17:00) [12]В потолке открылся люк - не волнуйтесь, это глюк (с)
sniknik (2006-07-25 09:12:00) [13]если чегото не может быть, но оно есть, то это точно глюк... того кто его видит... т.к. если его можно описать и повторить у других то это уже будет баг.
Sergey13 (2006-07-25 09:06:00) [14]> [4] yaral © (25.07.06 08:55)
> Причем тут кофе?
Ты считаешь - это чудо? Я думаю, что у тебя ошибка в программе.
Кто из нас прав - покажет время. 8-)
yaral (2006-07-25 09:04:00) [15]>> Johnmen © (25.07.06 08:58) [5]
Вот и я про тоже, вроде не должно такого быть то! Но есть!
Т.е. Это глюк сервера БД надо пологать?
Johnmen (2006-07-25 08:58:00) [16]
> как такое возможно?
Никак.
yaral (2006-07-25 08:55:00) [17]>> Sergey13 © (25.07.06 08:20) [3]
Причем тут кофе? Не сталкивался если с такой ситуацией, то вроде и писать не очем.
Просто оригинально, без индекса работает, с индексом нет, как такое возможно?
Sergey13 (2006-07-25 08:20:00) [18]2 [2] yaral © (25.07.06 06:34)
> Почему это может быть?
Я еще кофе не пил, потому гущи нет - гадать не на чем.
yaral (2006-07-25 06:34:00) [19]Проверил, не помогло, не в этом дело. Нашел один индекс, его удаляю, все выполняется правильно, добавляю обратно, выполняется не правильно. Почему это может быть?
Sergey13 (2006-07-24 14:38:00) [20]2 [0] yaral © (24.07.06 14:32)
> Может версия сервера с багами? Использую FB 1.5.0.4306.
Кто мешает скачать последнюю версию и проверить?