Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/delphi/9.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/scala/19.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Multithreading 将值传递给onTerminate with AnonymousThread_Multithreading_Delphi_Delphi Xe2 - Fatal编程技术网

Multithreading 将值传递给onTerminate with AnonymousThread

Multithreading 将值传递给onTerminate with AnonymousThread,multithreading,delphi,delphi-xe2,Multithreading,Delphi,Delphi Xe2,我有一个正在运行的线程应用程序,它正在计算一些更长的计算 procedure TForm.calculationInThread(value: Integer); var aThread : TThread; begin aThread := TThread.CreateAnonymousThread( procedure begin myCalculation(value); end ); aTh

我有一个正在运行的线程应用程序,它正在计算一些更长的计算

procedure TForm.calculationInThread(value: Integer);
var aThread : TThread;
begin
  aThread :=
    TThread.CreateAnonymousThread(
      procedure
      begin
        myCalculation(value);           
      end
    );
  aThread.FreeOnTerminate := True;
  aThread.OnTerminate := self.calculationInThreadEnd;
  aThread.Start;
end; 
以及计算结束的实现

procedure TForm.calculationInThreadEnd(Sender: TObject);
begin
   doSomething;
end;
我可能会错过一些愚蠢的事情,但如何将值传递给计算结束?我发现

TThread.SetReturnValue(value);
但我如何在onTerminate通话中访问它

解决方案

OnTerminate事件的发送方参数是thread对象。所以你可以这样做:

aThread :=
  TThread.CreateAnonymousThread(
    procedure
    begin
      myCalculation(value);           
      TThread.SetReturnValue(...);
    end
  );
然后在OnTerminate事件处理程序中,您可以执行以下操作:

procedure TForm.calculationInThreadEnd(Sender: TObject);
var
  Value: Integer;
begin
  Value := (Sender as TThread).ReturnValue;
end;
更新


返回值属性受保护,因此您需要使用受保护的hack来访问它。

我不能这样访问它,它会失败,出现错误[dcc32 error]Unit1.pas33:E2362无法访问受保护的符号TThread.ReturnValue,并且TThread不包含名为“ReturnValue”的成员,请使用受保护的hack。然而,所有这些挣扎表明,整个方法并不是最好的方法。CreateAnonymousThread返回TThread,因此即使我尝试使用proteceted hack,它也会编译,但会因类类型转换无效而崩溃。我喜欢AnonymousThread,因为它很简单,我不需要在它启动后访问正在运行的线程,我只想知道,调用CalculationThreadEnd时哪个线程结束了。Ofc我可以制作一个列表fifo或类似的东西,在那里添加线程标识符,并在CalculationThreadEnd函数中处理它。但我认为会有一个更优雅、更干净的解决方案。在保护黑客方面效果很好。你是对的,我错过了另一个黑客角色。对于任何更复杂的问题,我想我将使用不同的方法,在这种情况下,为了简单起见,我将使用hack。
procedure TForm.calculationInThreadEnd(Sender: TObject);
var
  Value: Integer;
begin
  Value := (Sender as TThread).ReturnValue;
end;