この質問は些細なことのように思えるかもしれませんが、無視しないでください。
通常、TThread オブジェクトを破棄する前に、TThread.Execute() メソッドを呼び出したスレッドが終了するまで待機する必要があります。これは、たとえば、クラスのデストラクタ内で破棄されたオブジェクトがアクセスされなくなったことを確認できるからです。したがって、Terminate を呼び出して終了するかどうかを知るためにスレッドがチェックする必要のある Terminated フラグを設定してから、WaitFor() メソッドを呼び出す必要があります。
スレッドが一時停止している可能性があるため、WaitFor を呼び出す前にスレッドを再開するのがよいと思います。そうしないと、呼び出し元のスレッドがデッドロックしてしまいます。また、スレッドは複数回中断できるため、同じ回数だけ再開する必要がありますよね?
while Suspended do
Resume;
スレッドがサスペンド状態で作成された場合、スレッドを終了するためだけにスレッドを再開するときに TThread.Execute() メソッドが呼び出されることを心配する必要はありません (間違っていたら訂正してください)。
私が述べたことは、解放される各 TThread オブジェクトに対して次のコード行を使用することを提案しています。
MyThread.Terminate;
while MyThread.Suspended do
MyThread.Resume;
MyThread.WaitFor;
MyThread.Free;
残念ながら、複数のスレッドを作成したアプリケーションを破棄する場合、破棄される TThread オブジェクトごとにそのようなコードを不必要に記述すると、コードが非常に長くなり、場合によっては不透明になります。
したがって、これらすべてを TThread クラスのオーバーライドされたデストラクタ内に配置できるという結論に達しました。そのおかげで、破棄されたかどうかを気にせずに MyThread.Free (または MyThread.FreeOnTerminate が設定されている場合は MyThread.Terminate) を呼び出すだけで十分です。 object が TThread オブジェクトかどうか:
destructor TMyThread.Destroy;
begin
//if FreeOnTerminate, the calling thread cannot wait for itself
if GetCurrentThreadId <> ThreadId then
begin
Terminate;
while Suspended do
Resume;
WaitFor;
end;
{free all objects created in this class}
inherited Destroy;
end;
こんな初歩的な質問ですみません。ただし、TThread オブジェクトを破棄するこの方法 (普遍的な方法であることを願っています) について、あなたの意見を知りたいと思います。同僚のコードから、彼らは通常、最初のコード例を使用してそのようなオブジェクトを破棄することを学びましたが、待機中のスレッドが中断されていないかどうかを確認することは一度もありませんでした。コードのどこかで中断されている可能性があります。したがって、コードをより明確かつ安全にする、このクラスのオブジェクトを破棄する普遍的な方法を見つけようとしました。私はそれを悪化させなかったことを願っています - あなたはどう思いますか?
事前にご提案いただきありがとうございます。