Форум: "WinAPI";
Текущий архив: 2006.04.16;
Скачать: [xml.tar.bz2];
ВнизПоток не выполняет Execute без WaitFor. Что не так? (+) Найти похожие ветки
← →
EarlVadim © (2006-01-24 19:47) [0]Если при вызове потока стоит WaitFor - то всё работает, но программа ждёт выполнения потока и смысл его (потока) теряется. Мы тупо сидим и ничего в проге не можем делать.
Если снять WaitFor, то процедура потока EXECUTE - не получает управления. Пробовал самые разные варианты вызова потока - ничего не лечит. Уже понял, что где-то что-то не так В ПРИНЦИПЕ. Подскажите, уже 2 дня убил....
Привожу UNIT целиком......
unit MyThreadU;
interface
uses
Classes, Windows, SysUtils;
type
MyThread = class(TThread)
private
CF : array of String;
FOutPar : array of String;
FReady : array of boolean;
ST : TStrings;
Lens : integer;
protected
procedure Execute; override;
public
constructor Create(InPar : array of String);
function GetFReady(Index: Integer): Boolean;
function GetFOutPar(Index: Integer): String;
property OutPar[Index: Integer] : String Read GetFOutPar;
property Ready[Index: Integer]: Boolean Read GetFReady;
end;
implementation
constructor MyThread.Create(InPar : array of String);
Var
i : integer;
begin
Lens:= Length(InPar);
SetLength(CF,Lens);
SetLength(FReady,Lens);
SetLength(FOutPar,Lens);
For i:= 0 to Lens-1 do begin
CF[i]:= InPar[i];
FReady[i]:= false;
end;
// скопировали входной массив строк
inherited Create(false);
// после этого Execute не выполняется
end;
function MyThread.GetFReady(Index: Integer): boolean;
begin
If Index <= Lens-1 then Result:= FReady[Index];
end;
function MyThread.GetFOutPar(Index: Integer): string;
begin
If Index <= Lens-1 then Result:= FOutPar[Index];
end;
procedure MyThread.Execute;
Var
i : integer;
begin
For i:= 0 to Lens-1 do begin
st:= TStringList.Create;
try
If FileExists(PChar(CF[i])+"\unitinfo.txt") then begin
st.LoadFromFile(PChar(CF[i])+"\unitinfo.txt");
FOutPar[i]:= ST.Strings[1];
end else FOutPar[i]:= "";
finally
FReady[i]:= true;
st.free;
end;
end;
end;
end.
Теперь в программе
Var
HostPath : array of string
Procedure TMainForm.ReadData(Sender: TObject);
Thread := MyThread.Create(HostPath); // список хостов
//прочитан из ini ранее
Thread.Priority := tpLowest;
Thread.FreeOnTerminate := false;
// Thread.WaitFor; {без WaitFor - не работает, а с ним - примораживает. }
For i:= 0 to Hosts-1 do begin
Labels[i].Caption:= Thread.OutPar[i];
end;
Thread.Destroy;
end;
← →
begin...end © (2006-01-24 20:29) [1]> EarlVadim © (24.01.06 19:47)
> Thread := MyThread.Create(HostPath);
> ...
> Thread.Destroy; <-- !!!
Создаём экземпляр класса MyThread. В параллельном потоке начинает работать поточная функция (которая и должна, по идее, исполнять код метода Execute). Тем временем, в основном потоке ВЫЗЫВАЕТСЯ DESTROY, который первым делом устанавливает флаг Terminate в True. В параллельном потоке только что запущенная поточная функция обнаруживает, что флаг Terminated уже выставлен, и просто не приступает к исполнению метода Execute.
← →
ANB © (2006-01-24 22:33) [2]1. А так ли уж тут нужен поток ? Может Application.ProcessMessages после каждой итерации попроще будет ?
2. Если уж сильно хотите поток, то перед его уничтожением все равно придется ждать, пока он завершится. WaitFor остановит основной поток, так что лучше ждать в цикле какого нибудь флага, выдавая в нем же Application.ProcessMessages, чтобы основной поток "жил".
← →
EarlVadim © (2006-01-25 12:38) [3]begin...end © (24.01.06 20:29) [1]
Да, все верно. Спасибо.
> 1. А так ли уж тут нужен поток ?
Однозначно нужен. Представь цикл из нескольких десятков сетевых файлов.. А в один поток программа "жить" несколько минут будет оч-ч-чень плохо.
Но флаг для ожидания у меня как-раз предусмотрен FReady.
В общем заработало все... спасибо.
Страницы: 1 вся ветка
Форум: "WinAPI";
Текущий архив: 2006.04.16;
Скачать: [xml.tar.bz2];
Память: 0.46 MB
Время: 0.04 c