Страница 1 из 1
Выполнение скрипта через dbexpress
Добавлено: 04 дек 2006, 09:02
vayer
Для набора записей в цикле вызываю хранимую процедуру, в качестве параметров которой передаю данные записей.
Ну очень медленно работает. Нельзя ускорить, например, через пакетную обработку либо выполнение скрипта (сохранить в файл, а затем выполнить скрипт) ???
Добавлено: 04 дек 2006, 10:01
kdv
без разницы - если ты медленно сделал, то будет что в скрипте, что через dbexpress, скорее всего. Если, конечно, ты после выполнения каждого оператора не перечитываешь наборы данных.
Re: Выполнение скрипта через dbexpress
Добавлено: 04 дек 2006, 11:14
WildSery
vayer писал(а):Нельзя ускорить, например,
Пока не увижу, что именно у тебя делается, и на какой версии сервера, не скажу.
Добавлено: 05 дек 2006, 07:06
vayer
Вот часть кода:
Код: Выделить всё
with SQLProc do
begin
StoredProcName:='UPDATE_MENU_ITEM';
Params.Clear;
P1:=TParam.Create(Params,ptInput);
P2:=TParam.Create(Params,ptInput);
P3:=TParam.Create(Params,ptInput);
P4:=TParam.Create(Params,ptInput);
P5:=TParam.Create(Params,ptInput);
P6:=TParam.Create(Params,ptInput);
P1.Name:='ID';
P2.Name:='NAME'; P2.Size:=40;
P3.Name:='PRICE';
P4.Name:='IS_GROUP';
P5.Name:='UP_ID';
P6.Name:='ID_PLACE';
P6.asinteger:=DM.FirmId;
SQLProc.Prepared:=true;
end;
with dbxSHMenu do
//именно в этом цикле тормоз
while not EOF do
begin
P1.asinteger:=FieldByName('id').asinteger;
P2.asstring:=FieldByName('name').asstring;
P3.asfloat:=FieldByName('price').asfloat;
P4.asinteger:=FieldByName('is_group').asinteger;
P5.asinteger:=FieldByName('up_id').asinteger;
SQLProc.ExecProc;
Next;
end;
Сервер - Firebird 1.5, подключаюсь по TCP
В хранимой процедуре, вызываемой в цикле, идет простой insert into.
Цикл перебирает порядка 2000 записей.
Пробовал убирать Foreign Keys из таблицы, куда происходит вставка, - прирост скорости есть, но незначительный (вместо 50 сек. - 40).
Если вместо dbexpress использовать FIBPlus, будет быстрее работать???
Добавлено: 05 дек 2006, 09:43
kdv
Если вместо dbexpress использовать FIBPlus, будет быстрее работать???
незначительно. покажи лучше код процедуры.
Добавлено: 05 дек 2006, 17:55
Merlin
И инсёртного триггера заодно.
Добавлено: 05 дек 2006, 19:13
WildSery
vayer писал(а):В хранимой процедуре, вызываемой в цикле, идет простой insert into.
Если простой INSERT, то почему процедура, а не
Код: Выделить всё
insert into Menu_Item (id, name, price, is_group, up_id, id_place)
values (:id, :name, :price, :is_group, :up_id, :id_place);
Добавлено: 06 дек 2006, 04:30
vayer
kdv писал(а):Если вместо dbexpress использовать FIBPlus, будет быстрее работать???
незначительно. покажи лучше код процедуры.
Код: Выделить всё
CREATE PROCEDURE UPDATE_MENU_ITEM (
id integer,
name varchar(40),
price double precision,
is_group integer,
up_id integer,
id_place integer)
as
declare variable aid integer;
begin
/* Procedure Text */
if (:is_group=1) then
begin
aid=0;
select id from menu_groups where id=:id and id_place=:id_place into :aid;
if (:aid>0) then
begin
update menu_groups
set name=:name, up_id=:up_id, state=1
where id=:id and id_place=:id_place;
end
else
begin
insert into menu_groups
(id,id_place,name,up_id,state)
values (:id,:id_place,:name,:up_id,1);
end
end
else
begin
aid=0;
select id from menu_items where id=:id and id_place=:id_place into :aid;
if (:aid>0) then
begin
update menu_items
set name=:name, price=:price, up_id=:up_id, state=1
where id=:id and id_place=:id_place;
end
else
begin
insert into menu_items
(id,id_place,name,price,up_id,state)
values (:id,:id_place,:name,:price,:up_id,1);
end
end
suspend;
пробовал убирать условия, оставлял просто insert - прироста скорости почти не было
Добавлено: 06 дек 2006, 04:33
vayer
WildSery писал(а):Если простой INSERT, то почему процедура, а не
Код: Выделить всё
insert into Menu_Item (id, name, price, is_group, up_id, id_place)
values (:id, :name, :price, :is_group, :up_id, :id_place);
А что, если просто выполнять sql-оператор вроде insert'а через dbexpress, быстрее будет???
Добавлено: 06 дек 2006, 04:34
vayer
Merlin писал(а):И инсёртного триггера заодно.
Тригера нет
Добавлено: 06 дек 2006, 10:05
kdv
так. что-то я не вижу проблемы, по крайней мере с процедурой. впору товарищу профайлер на своей программе запускать. Или попробовать аналогичное на ibx написать, вдруг в dbexpress что-то не так.
Добавлено: 06 дек 2006, 10:42
vayer
kdv писал(а):так. что-то я не вижу проблемы, по крайней мере с процедурой. впору товарищу профайлер на своей программе запускать. Или попробовать аналогичное на ibx написать, вдруг в dbexpress что-то не так.
Зачем профайлер???? Уже проверял, тормозит именно в указанном цикле на вызове хранимой процедуры. Может, действительно, попробовать что-нибудь вроде FIBPlus? НО, где-то читал, что вообще-то не рекомендуется заниматься последовательной вставкой большого числа записей на interbase/firebird, а лучше это делать пакетной обработкой. Я так понимаю, через скрипт. Кстати, пробовал выполнить скрипт, соответствующий указанному циклу, в IBExpress - выполнился за 9 сек.!!!!
Добавлено: 06 дек 2006, 10:43
vayer
А как выполнить скрипт встроенными средствами на Delphi?
Добавлено: 06 дек 2006, 11:31
WildSery
Что-нибудь типа TIBScript.
А если сервер FB2, то можно в несколько execute block затолкать, будет ещё быстрее.
Добавлено: 06 дек 2006, 11:45
kdv
вполне возможно, что dbexpress ведет себя с транзакциями так же, как и BDE. т.е. при выполнении ХП пытается тут же сделать commit со всеми вытекающими. Потому я и советовал профайлер.
Значит, как минимум, надо бы указанный код обрамить стартом и коммитом транзакции, и посмотреть, не будет ли быстрее.
Добавлено: 07 дек 2006, 04:47
vayer
WildSery писал(а):Что-нибудь типа TIBScript.
А если сервер FB2, то можно в несколько execute block затолкать, будет ещё быстрее.
А можно подробнее про execute block, или, может быть, подскажите, где почитать про отличия FB2 от FB 1.5 и про перенос базы под FB2?
Добавлено: 07 дек 2006, 04:48
vayer
kdv писал(а):вполне возможно, что dbexpress ведет себя с транзакциями так же, как и BDE. т.е. при выполнении ХП пытается тут же сделать commit со всеми вытекающими. Потому я и советовал профайлер.
Значит, как минимум, надо бы указанный код обрамить стартом и коммитом транзакции, и посмотреть, не будет ли быстрее.
Скорее всего именно в этом дело, но как через dbexpress работать с транзакциями?
Добавлено: 07 дек 2006, 10:01
kdv
Скорее всего именно в этом дело, но как через dbexpress работать с транзакциями?
действительно, как же? Может быть, прочитать хелп? Или, прочитать
www.ibase.ru/devinfo/dbexpress.htm ?
Добавлено: 07 дек 2006, 12:39
WildSery
vayer писал(а):А можно подробнее про execute block, или, может быть, подскажите, где почитать про отличия FB2 от FB 1.5 и про перенос базы под FB2?
http://www.ibase.ru/firebird/Firebird_v ... eNotes.pdf
Добавлено: 08 дек 2006, 05:57
vayer
Спасибо всем за помощь.
Перписал все через FIBPlus, ограничил цикл транзакцией - стало выполняться за 2 сек.