Страница 1 из 1

Импорт большого обьема - жуткие тормоза

Добавлено: 30 ноя 2005, 10:18
Ugrael
Доброго времени суток.
Есть такакя проблема-есть база. сней работают 2 человека.
они паралельно делают либо импорт из dbf файла либо печать множества записей. Так вот когда начинается импорт или печать то база словно переходит в однопользовательский режим. пока не пройдет печать или импорт другой человек вообще не может вводить\печатать записи. Люди жалуются и вообщем то справедливо.
как это делается. Одна database, одна транзакция (read commited). несколько dataset-ов. Импорт идет в отдельную таблицу, где записи обрабатываются и потом переносятся в главную таблицу. печать идет сразу из главной. прошу помощи.спасибо.

Re: Импорт большого обьема - жуткие тормоза

Добавлено: 30 ноя 2005, 10:25
ZMan
Ugrael писал(а):Так вот когда начинается импорт или печать то база словно переходит в однопользовательский режим. пока не пройдет печать или импорт другой человек вообще не может вводить\печатать записи.
Опиши подробнее, как проделываешь импорт?

Re: Импорт большого обьема - жуткие тормоза

Добавлено: 30 ноя 2005, 10:43
Ugrael
ZMan писал(а):Опиши подробнее, как проделываешь импорт?
импорт из dbf файла в цикле построчно.
то бишь insertrecord(...), next

Re: Импорт большого обьема - жуткие тормоза

Добавлено: 30 ноя 2005, 11:40
ZMan
Ugrael писал(а):
ZMan писал(а):Опиши подробнее, как проделываешь импорт?
импорт из dbf файла в цикле построчно.
то бишь insertrecord(...), next
Мало информации. Желательно полностью код как ты это дело вытягиваешь и записываешь.

Re: Импорт большого обьема - жуткие тормоза

Добавлено: 30 ноя 2005, 11:46
Ugrael
DataModule1.importdbf.First;
for i:=1 to DataModule1.importdbf.RecordCount do
begin
DataModule1.NolDataSet.Insert;
DataModule1.NolDataSet.FieldByName('fam').AsString:=DataModule1.importdbf.FieldByName('fam').AsString;
DataModule1.NolDataSet.FieldByName('imq').AsString:=DataModule1.importdbf.FieldByName('imq').AsString;
DataModule1.NolDataSet.FieldByName('otc').AsString:=DataModule1.importdbf.FieldByName('otc').AsString;
DataModule1.NolDataSet.FieldByName('DATA_R').AsString:=DataModule1.importdbf.FieldByName('DATA_R').AsString;
DataModule1.NolDataSet.Post;
oper.glavTransaction.Commit;
DataModule1.NolDataSet.Active:=true;
DataModule1.importdbf.Next;
end;


Вот так. Только полей конечно больше ( 20 )

Re: Импорт большого обьема - жуткие тормоза

Добавлено: 30 ноя 2005, 11:47
Ugrael
DataModule1.importdbf.First;
for i:=1 to DataModule1.importdbf.RecordCount do
begin
DataModule1.NolDataSet.Insert;
DataModule1.NolDataSet.FieldByName('fam').AsString:=DataModule1.importdbf.FieldByName('fam').AsString;
DataModule1.NolDataSet.FieldByName('imq').AsString:=DataModule1.importdbf.FieldByName('imq').AsString;
DataModule1.NolDataSet.FieldByName('otc').AsString:=DataModule1.importdbf.FieldByName('otc').AsString;
DataModule1.NolDataSet.FieldByName('DATA_R').AsString:=DataModule1.importdbf.FieldByName('DATA_R').AsString;
DataModule1.NolDataSet.Post;
oper.glavTransaction.Commit;
DataModule1.NolDataSet.Active:=true;
DataModule1.importdbf.Next;
end;


Вот так. Только полей конечно больше ( 20 )

Добавлено: 30 ноя 2005, 12:11
kdv
судя по всему, ты не читал ни www.ibase.ru/devinfo/ibx.htm ни
www.ibase.ru/devinfo/impexp.htm

т.к. вставлять в базу таким способом - dataset.insert/post , да еще делать commit каждый раз, это самый худший способ, который можно придумать.

Re: Импорт большого обьема - жуткие тормоза

Добавлено: 30 ноя 2005, 12:32
ZMan
Ugrael писал(а): for i:=1 to DataModule1.importdbf.RecordCount do
begin
DataModule1.NolDataSet.Insert;
...
DataModule1.NolDataSet.Post;
oper.glavTransaction.Commit;
...
end;
Во-первых, так делать нельзя! Commit делается после вставки минимум 200 записей, тем более dbf.
Ugrael писал(а):DataModule1.importdbf.First;
for i:=1 to DataModule1.importdbf.RecordCount do
begin
...
oper.glavTransaction.Commit;
DataModule1.NolDataSet.Active:=true;
DataModule1.importdbf.Next;
end;
Во-вторых, сам логически подумай, что ты делаешь?
1. становишься на первую запись;
2. в циксе комитешь базу;
3. после комита становишься на след. запись. После какой записи?!
Ответ: всегда после первой.

Я, вообще, не в понятках! Как, вообще, завершается такой цикл???! :shock: :?:


Решение:
1. Вынеси комит из цикла и удали строчку
...
DataModule1.NolDataSet.Active:=true;
...
А. вообще, когда нужно заинсертить записи, я делаю так

Код: Выделить всё

First
while not EOF do
begin
  SQL.Text:='insert into Table (Field1, Field2,...,FieldN) values (:Param1, :Param2,...,:ParamN)';
  for i:= 0 to Params.Count-1 do
   begin
     Params[i].AsVariant:=ValueN; //где ValueN - любой источник данных(запрос, массив и тд и др)
   end
  Next;
end;
Commit; //если нужен

Добавлено: 30 ноя 2005, 16:30
Ugrael
заканчваться то заканчивается цикл. некст то я делаю dbf файлу.
а вот насчет commit - это я да, пролетел .... 8(

чуть позже опробую твой способ.

и , логически рассуждая, я так понимаю, что должно быть быстрее если загнать сначала dbf куда нибудь. например в память ?

Добавлено: 01 дек 2005, 08:25
Ivan_Pisarevsky
должно быть быстрее если загнать сначала dbf куда нибудь. например в память ?
напимер в экстернал тэйбл :wink:

Добавлено: 01 дек 2005, 13:56
MMF
Еще выкинь из цикла все FieldByName

Добавлено: 16 дек 2005, 10:42
Ugrael
MMF писал(а):Еще выкинь из цикла все FieldByName
а что поставить ?

с помощью инсерт быстро, но это сначала приходится конвертить дбф.
лишнее звено....