![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Потоки TTread
Helen © (2005-07-15 10:00:00)Добрый день! Помогите, пожалуйста разобраться новичку! Только начинаю работать с потоками. Создаю поток, по клику на кнопку он должен прерваться, т.е. MyThread.Terminate. Причем должно выполниться событие OnTerminate, в котором кое-какие действия с VCL-компонентами. Почему-то событие не наступает, а поток продолжает выполняться после некоторой задержки.
Digitman (2005-07-15 11:16:00) [1]у тебя в теле Execute() возникает необработанное исключение
возникает оно здесь - fmLoadData.Memo1.Lines.Add() - и связано с попыткой обращения к виз.VCL-контролу в контексте неосновного потока, что недопустимо
см. метод Synchronize()
Helen (2005-07-15 10:58:00) [2]
fmLoadData.Memo1.Lines.Add(' * * *');
{$I-}
AssignFile(ProgressFile, ExtractFilePath(Application.ExeName)+'ñòàòèñòèêà çàãðóçêè.txt');
if not FileExists(ExtractFilePath(Application.ExeName)+'ñòàòèñòèêà çàãðóçêè.txt') then Rewrite(ProgressFile)
else Append(ProgressFile);
IOResult;
{$I+}
Writeln(ProgressFile,' ');
Data.qrTemp.Open;
DataFile:='St'+stD+stM+RightStr(stY,2)+'.dbf';
while not Data.qrTemp.Eof and (not Terminated) do begin
fmLoadData.Memo1.Lines.Add('Íà÷àëî çàãðóçêè äàííûõ ïî ñòàíöèè '+Data.qrTemp.FieldByName('Name').AsString);;
NetResource.dwType:= RESOURCETYPE_DISK;
NetResource.lpLocalName:= nil;
NetResource.lpRemoteName:= Pchar(Data.qrTemp.FieldByName('IPStation').AsString);
NetResource.lpProvider := '';
if (WNetAddConnection2(NetResource,
PChar(Data.qrTemp.FieldByName('Password').AsString),
PChar(Data.qrTemp.FieldByName('Login').AsString),
0) = NO_ERROR)
then begin
DatabaseName:= Data.qrTemp.FieldByName('IPStation').AsString;
if not FileExists(DatabaseName+'\'+DataFile)
then begin
Writeln(ProgressFile, DateTimeToStr(Now()) + ':00:00 '+Data.qrTemp.FieldByName('Name').AsString+' Äàííûå íå çàãðóæåíû, ò.ê. íå íàéäåí ôàéë ñ äàííûìè '+DatabaseName+'\'+DataFile+'!');
WNetCancelConnection2(Pchar(Data.qrTemp.FieldByName('IPStation').AsString), 0,TRUE);
Data.qrTemp.Next;
Continue;
end;
for i:=HourB to HourE do begin
запрос данных
while not Data.QueryDBF.Eof and (not Terminated) do
begin
преобразование и запись данных в базу
end;
end;
end;//for i:=HourB to HourE do
WNetCancelConnection2(Pchar(Data.qrTemp.FieldByName('IPStation').AsString), 0,TRUE);
Writeln(ProgressFile, DateTimeToStr(Now()) + ':00:00 '+Data.qrTemp.FieldByName('Name').AsString+' Äàííûå ñòàòèñòèêè çàãðóæåíû!');
fmLoadData.Memo1.Lines.Add(Data.qrTemp.FieldByName('Name').AsString+': Äàííûå ñòàòèñòèêè çàãðóæåíû!');
end else begin
fmLoadData.Memo1.Lines.Add(' '+SysErrorMessage(GetLastError)+':'+Data.qrTemp.FieldByName('Name').AsString);
Writeln(ProgressFile, DateTimeToStr(Now()) + ':00:00 '+Data.qrTemp.FieldByName('Name').AsString+' Äàííûå íå çàãðóæåíû, ò.ê. íå ìîãó ïîäêëþ÷èòü ñåòåâîé ðåñóðñ '+Data.qrTemp.FieldByName('IPStation').AsString+'!');
end; // åñëè ñìîãëè ïîäêëþ÷èòü ñåòåâîé ðåñóðñ
Data.qrTemp.Next;
end; // while not Data.qrTemp.Eof do
Digitman (2005-07-15 10:43:00) [3]
> Helen (15.07.05 10:39) [7]
это все - вокруг да около.
самое интересное - это тело Execute() ..
Helen (2005-07-15 10:42:00) [4]Digitman © (15.07.05 10:17) [5]
Попробовала поставить проверку выполнения условия Terminated=True, почему-то она игнорируются и поток выполняется дальше
Helen (2005-07-15 10:39:00) [5]Дело в том, что по мере выполнения потока, он выдает в Memo некоторые сообщения о ходе выполнения. По событию OnTerminate в Memo добавляются несколько строк и др.
Создаю поток:
ThreadLoadManual:=TMainThread.Create(True);
ThreadLoadManual.Priority:=tpLowest;
ThreadLoadManual.OnTerminate:=HandleTerminateManual;
ThreadLoadManual.FreeOnTerminate:=True;
ThreadLoadManual.Resume;
Событие OnTerminate:
procedure TfmLoadData.HandleTerminateManual(Sender:TObject);
begin
CloseFile(ProgressFile);
fmLoadData.Memo1.Lines.Add('...');
fmLoadData.btnStatistica.Enabled:=True;
fmLoadData.Height:=495;
fmLoadData.rgStatistica.Enabled:=True;
end;
Digitman (2005-07-15 10:18:00) [6]
> Kolan © (15.07.05 10:12) [4]
по дифолту вызов обработчика OnTerminate уже синхронизирован
Digitman (2005-07-15 10:17:00) [7]
> ничего такого у меня нет
поточная ф-ция должна каким-то образом быть извещена о необходимости "закругляться по хозяйству"
периодическая (как можно чаще) проверка выполнения условия Terminated=True как вариант позволяет получить такое "извещение"
метод TThread.Terminate просто устанавливает этот флаг, не более того
Kolan (2005-07-15 10:12:00) [8]
> Helen (15.07.05 10:00)
С VCL компонентами должен работать главный поток.
Дальше без кода говорить неочем..
Helen (2005-07-15 10:09:00) [9]Чапаев © (15.07.05 10:05) [1]
Да нет, ничего такого у меня нет.
Alexander Panov (2005-07-15 10:06:00) [10]Чапаев © (15.07.05 10:05) [1]
Ну ты телепат!
Чапаев (2005-07-15 10:05:00) [11]Посмтри примеры. У тебя в основном цикле должно быть что-то вроде while not Thread.Terminated do Work;