Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2003.01.06;
Скачать: CL | DM;

Вниз

Thread (будь он неладен)   Найти похожие ветки 

 
roman_tutov   (2002-12-22 18:18) [0]

Есть форма на которой находиться компонент pFibDatabase
В процессе работы программа запускает треды которые к этой компоненте обращаються . Проблема в том что два треда одновременно запущенные не могут работать с вышеуказанным компонентом . Вопрос :
как эту проблему обойти . Или для каждого треда нужен свой источник данных ? Как мне в треде (который не имеет своей формы) использовать свой компонент . Пока я все налепил на Form1 и из треда обращаюсь form1.,блаблабла Что не есть правильно .

Заранее спасибо за ответ


 
asmith   (2002-12-22 19:34) [1]

Просто пиши в функции потока код для создания и уничтожения нужных тебе компонентов, что-то вроде
...
thisThreadIBDB := TIBDatabase.Create(Application) do
// установи параметры, создай и используй datasets
thisThreadIBDB.Free();


 
Roman_Tutov   (2002-12-23 09:07) [2]

А что значит параметр Application ? а то у меня компилятор
на строку
pFIBDatabase:= TpFIBDatabase.Create(Application);
ругаеться
[Error] Tread1.pas(31): Undeclared identifier: "Application"
Причем в Var прописано
pFIBDatabase:TpFIBDatabase;


 
Smithson ©   (2002-12-23 09:37) [3]

uses Forms


 
Roman_Tutov   (2002-12-23 11:19) [4]

Спасибо


 
Roman_Tutov   (2002-12-23 16:35) [5]

Сделал как выше советовали . Все-равно в одном потоке работает , а если попытаться запустить несколько потоков то они все останавливаються. Причем что происходит понять не могу .
Может есть какая-нибудь хитрость ?


 
Smithson ©   (2002-12-23 16:49) [6]

В каждом потоке должен быть свой NMHTTP. В начале execute создается, в конце освобождается.


 
Roman_Tutov   (2002-12-23 16:58) [7]

я в потоках работаю с БД .
В коде потока создаю бд
MypFIBDatabase:= TpFIBDatabase.Create(Application);
Как поток сделал что нужно делаю
MypFIBDatabase.Free;
И пока запущен один поток все прекрасно работает .
Если запустить 2й , то в обоих потоках происходит
disconnect от базы



 
Smithson ©   (2002-12-23 17:00) [8]

Хто такой TpFIBDatabase?
Если это эквивалент стандартного session, то он дожен быть один на
программу. А вот все запросы к базе должны быть индивидуальны для каждого потока.


 
Digitman ©   (2002-12-23 17:14) [9]


> Roman_Tutov


Никаких Application в кач-ве владельца !

MypFIBDatabase:= TpFIBDatabase.Create(nil);
try
finally
MypFIBDatabase.Free;
end;


> Smithson



> Если это эквивалент стандартного session, то он дожен быть
> один на программу


TSession - не thread-safe компонент. Недопустимо обращаться к сессии, созданной в одном потоке, из другого. Каждый поток обязан создавать свои собственные сессии


 
Smithson ©   (2002-12-23 17:36) [10]

Может быть. Я пользую ODAC - у него проблем не возникает при многопоточности. Хотя не знаю, предназначена ли его TOraSession для такой работы.


 
Roman_Tutov   (2002-12-24 09:40) [11]

Я хочу привести вырезку кода

MypFIBTransaction1:= TpFIBTransaction.Create(nil);
MypFIBDatabase:= TpFIBDatabase.Create(Application);
MypFibDataset3:= TpFIBDataset.Create(nil);

MypFIBTransaction1.DefaultDatabase:=MyPFIBDatabase;

MypFIBDatabase.DatabaseName:=host;
MypFIBDatabase.SQLDialect:=3;
MypFIBDatabase.DBParams.Add("lc_ctype=WIN1251");
MypFIBDatabase.DBParams.Add("password=secretpasswd");
MypFIBDatabase.DBParams.Add("user_name=myname");
MypFIBDatabase.DefaultTransaction:=MypFIBTransaction1;
MypFIBDatabase.Timeout:=10000;
MypFIBDatabase.UseLoginPrompt:=false;
MypFIBDatabase.SynchronizeTime:=false;
MypFIBDatabase.WaitForRestoreConnect:=10000;
MypFIBDatabase.CacheSchemaOptions.AutoLoadFromFile:=false;
MypFIBDatabase.CacheSchemaOptions.AutoSaveToFile:=false;

MypFibDataset3.Database:=MypFIBDatabase;
MypFibDataset3.AutoCalcFields:=True;
MypFibDataset3.AutoCommit:=False;
MypFibDataset3.BufferChunks:=2048;
MypFibDataset3.CachedUpdates:=false;
MypFibDataset3.DataSet_ID:=0;
MypFibDataset3.Filtered:=false;
MypFibDataset3.Transaction:=MypFIBTransaction1;
MypFibDataset3.SQLs.SelectSQL.Add("SELECT * FROM TBL1");

try
begin
MypFIBDatabase.Connected:=true;
MypFIBDataSet3.Active:=true;
MypFIBDataSet3.First;
while not MypFIBDataSet3.Eof do
begin
{ковыряюсь в базе}
end;

MypFIBDataSet3.Next;
end;

except
end;

MypFIBDatabase.Connected:=false;

MypFIBDatabase.Free;
MypFIBTransaction1.Free;
MypFibDataset3.Free;

Вот этоткусок кода нормально работает в треде .НО ТОЛЬКо если тред один . Если запустить 2 треда то в обоих
MypFIBDatabase.connected становиться false
Куда копать ?


 
Roman_Tutov   (2002-12-24 09:51) [12]

упс
MypFIBDatabase:= TpFIBDatabase.Create(Application);
читать как
MypFIBDatabase:= TpFIBDatabase.Create(nil);


 
Digitman ©   (2002-12-24 11:02) [13]

Ну я надеюсь, что и MypFIBTransaction1,MypFIBDatabase и MypFibDataset3 - это у тебя поля поточного класса ? Или, на кр.случай - лок.переменные процедуры Execute ?


 
VaS ©   (2002-12-24 11:56) [14]

Да, и есть еще такое недокументированное ключевое слово в языке - "with".


 
Roman_Tutov   (2002-12-24 12:11) [15]

MypFIBTransaction1,MypFIBDatabase и MypFibDataset3 это локальные
переменные процедуры Execute

To VaS
Что за "with" и к чему оно мне ?


 
VaS ©   (2002-12-24 12:19) [16]

With не тебе надо, а нам, чтобы код читался лучше. Заботиться надо о людях. Эх, молодежь...


 
Digitman ©   (2002-12-24 12:40) [17]


> Если запустить 2 треда то в обоих
> MypFIBDatabase.connected становиться false


И как ты определил это ? Ты брейкпойнт ставил ? Где ставил, в какой точке ?


 
Roman_Tutov   (2002-12-24 12:58) [18]

Я пошагово весь тред прошел


 
Digitman ©   (2002-12-24 13:05) [19]

Ну и ? В какой точке обнаружил сабж ?


 
Roman_Tutov   (2002-12-24 13:29) [20]

в MypFIBDatabase.Connected:=true;


 
Digitman ©   (2002-12-24 13:36) [21]

А с чего бы (до этого момента) базе уже быть Connected = True ?
Ты ж и строчку эту пишешь, для того чтобы активизировать новое соединение) ..


 
Vasya Pupkin   (2002-12-25 11:26) [22]

Я проблему решал следующим образом:
1. при инициализации создаю критическую секцию (один из объектов синхронизации)
2. при задействовании компонента в нескольких трэдах сначала вхожу в критическую секцию (EnterCriticalSection), работаю с компонентом, далее освобождаю критическую секцию (LeaveCriticalSection). Не забывать про Try ... Finally...LeaveCriticalSection ... End
3. при выгрузке удаляю критическую секцию.
Работает очень быстро!



Страницы: 1 вся ветка

Текущий архив: 2003.01.06;
Скачать: CL | DM;

Наверх




Память: 0.52 MB
Время: 0.013 c
4-15363
lds
2002-11-19 14:15
2003.01.06
Как вызвать диалог выбора файлов?


1-15066
Юра
2002-12-25 11:09
2003.01.06
Application.ProcessMessages


14-15300
AL2002
2002-12-13 15:17
2003.01.06
Год козла


7-15344
Rem
2002-10-26 16:52
2003.01.06
Установка своей графической оболочки (вместо explorer.exe)


6-15189
Ihor Borysyuk
2002-11-07 16:26
2003.01.06
Как в Делфе работать с SSL?