各种答案表明,睡在线程内是个坏主意,例如:避免睡眠。为什么?通常给出的一个原因是,如果它正在睡觉,很难优雅地退出线程(通过信号通知它终止)。
Various answers suggest it is a bad idea to sleep inside a thread, for example: Avoid sleep. Why exactly? One reason often given is that it is difficult to gracefully exit the thread (by signalling it to terminate) if it is sleeping.
假设我想定期检查新的文件在一个网络文件夹,也许每10秒一次。这对于优先级设置为低(或最低)的线程似乎是完美的,因为我不希望潜在的耗时的文件I / O影响我的主线程。
Let's say I wanted to periodically check for new files in a network folder, maybe once every 10s. This seems perfect for a thread with the priority set to low (or lowest) because I don't want the potentially time-consuming file I/O to impact my main thread.
有哪些替代方案?代码在Delphi中给出,但同样适用于任何多线程应用程序:
What are the alternatives? Code is given in Delphi but would apply equally to any multi-threaded application:
procedure TNetFilesThrd.Execute(); begin try while (not Terminated) do begin // Check for new files // ... // Rest a little before spinning around again if (not Terminated) then Sleep(TenSeconds); end; finally // Terminated (or exception) so free all resources... end; end;稍作修改可能是:
// Rest a little before spinning around again nSleepCounter := 0; while (not Terminated) and (nSleepCounter < 500) do begin Sleep(TwentyMilliseconds); Inc(nSleepCounter); end;但这还涉及到休眠...
but this still involves a Sleep...
推荐答案这样做的标准方法是等待取消事件。在伪代码看起来像这样:
The standard way to do this is to wait on a cancellation event. In pseudo code that looks like this:
while not Terminated do begin // Check for new files // ... // Rest a little before spinning around again FTerminationEvent.WaitFor(TenSeconds); end;为了终止你将覆盖 TerminatedSet :
procedure TMyThread.TerminatedSet; begin inherited; FTerminationEvent.SetEvent; // abandon the wait in the thread method end;对事件的等待超时或由于事件被发出信号而终止。这允许你的线程暂停一段时间,并不负担CPU,并且仍然响应终止请求。
The wait on the event either times out, or terminates because the event is signaled. This allows your thread to pause for a while and not burden the CPU, and yet also remain responsive to requests to terminate.
更多推荐
睡在线程内的替代方法
发布评论