线程.睡眠实现

本文关键字:实现 线程 | 更新日期: 2023-09-27 18:24:58

我很好奇Thread.Sleep是如何实现的。我在Reflector上查看了Thread.Sleep的实现。它调用以下函数:

[MethodImpl(MethodImplOptions.InternalCall), SecurityCritical]
private static extern void SleepInternal(int millisecondsTimeout);

有人知道这是在哪里定义的吗?我知道其他的替代方案,比如Task.Delay。但我对实际的实现细节很好奇。

线程.睡眠实现

Joe Duffy的《并发编程》一书提供了您需要的所有细节。但总结一下:

  • Thread.Sleep的行为类似于Win API函数SleepEx
  • 持续时间参数=0将导致当前线程屈服于具有相同或更高优先级的另一个线程
  • 持续时间参数>0将导致上下文切换,并且当前线程将保持等待状态,直到经过指定的时间(大约)
  • 线程将保持可报警状态,这意味着它可以通过QueueUserAPC处理APC方法,并将响应Thread.Interrupt调用

我建议浏览SSCLI代码,以便更全面地了解它是如何实现的。

关于您关于无法将线程重新用于其他工作的问题。。。我有点困惑。Thread.Sleep是一个自愿暂停,所以您(程序员)告诉线程不要再做任何工作。就像我上面提到的,据说线程是可报警的,所以你可以实际中断它,甚至强迫它通过APC方法进行工作。

有关在Thread.Sleep仍处于挂起状态时让.NET线程运行APC的详细信息,请参阅此问题。

Thread.Sleep()在被系统线程(实际线程,而不是用户线程)调用时,是一个挂钩到操作系统内核调度内部的调用,类似于进程睡眠。它将执行上下文(在内核进程级别可见)置于"睡眠"等待状态,因此在唤醒之前不消耗CPU。这不是一个繁忙的等待。

如果你想让它清醒和/或做其他事情,除了Thread.Sleep()之外,还可以使用其他机制。

如果您想重用线程,请使用await Task.Delay()