有没有一种方法可以无限期地暂停线程?

有没有一种方法可以无限期地暂停线程?,第1张

有没有一种方法可以无限期地暂停线程

永远不要使用

Thread.Suspend
。它的主要问题是,在挂起线程时,有99%的时间您不知道该线程在做什么。如果该线程持有锁,则可以更容易陷入死锁等情况。请记住,您正在调用的代码可能正在幕后获取/释放锁。Win32具有类似的API:
SuspendThread
ResumeThread
。以下文档为
SuspendThread
API的危害提供了很好的摘要:

http://msdn.microsoft.com/zh-
cn/library/ms686345(VS.85).aspx

此功能主要是供调试器使用的。它不打算用于线程同步。在拥有同步对象(例如互斥锁或关键节)的线程上调用SuspendThread会导致死锁,前提是该调用线程试图获取挂起线程拥有的同步对象。为了避免这种情况,应用程序中的一个不是调试器的线程应该向另一个线程发出信号以挂起自身。目标线程必须设计为监视此信号并适当响应。

无限期挂起线程的正确方法是使用

ManualResetEvent
。线程很可能正在循环执行某些工作。挂起线程的最简单方法是让线程在每次迭代中“检查”事件,如下所示:

while (true){    _suspendEvent.WaitOne(Timeout.Infinite);    // Do some work...}

您可以指定一个无限超时,这样当不通知事件时,线程将无限期阻塞,直到通知事件为止,线程将在该点从中断处继续恢复。

您可以这样创建事件:

ManualResetEvent _suspendEvent = new ManualResetEvent(true);

true
参数告诉事件以信号状态开始。

当您想暂停线程时,请执行以下 *** 作:

_suspendEvent.Reset();

并恢复线程:

_suspendEvent.Set();

您可以使用类似的机制向线程发出信号以退出并等待两个事件,以检测到哪个事件已被发出信号。

为了好玩,我将提供一个完整的示例:

public class Worker{    ManualResetEvent _shutdownEvent = new ManualResetEvent(false);    ManualResetEvent _pauseEvent = new ManualResetEvent(true);    Thread _thread;    public Worker() { }    public void Start()    {        _thread = new Thread(DoWork);        _thread.Start();    }    public void Pause()    {        _pauseEvent.Reset();    }    public void Resume()    {        _pauseEvent.Set();    }    public void Stop()    {        // Signal the shutdown event        _shutdownEvent.Set();        // Make sure to resume any paused threads        _pauseEvent.Set();        // Wait for the thread to exit        _thread.Join();    }    public void DoWork()    {        while (true)        { _pauseEvent.WaitOne(Timeout.Infinite); if (_shutdownEvent.WaitOne(0))     break; // Do the work here..        }    }}


欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/zaji/5559771.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-12-14
下一篇 2022-12-14

发表评论

登录后才能评论

评论列表(0条)

保存