我正在通过c#书阅读Jeffrey Richter的clr并感到不舒服,因为任务等待可能并不总是等待我引用
“当线程调用Wait方法时,系统会检查Task是否正常 线程正在等待的已经开始执行。如果有,那么 调用Wait的线程将阻塞,直到Task完成 运行。但如果任务还没有开始执行,那么 系统可以(取决于TaskScheduler)执行任务 使用调用Wait的线程。如果发生这种情况,那么线程 调用Wait不会阻塞;它执行任务并返回 立即“。
有人可以分享更多见解,在这种情况下可能会出现这种情况吗?
答案 0 :(得分:12)
我认为这是不幸的措辞。并不是Wait
调用在任务完成执行之前返回;调用Wait
的线程可能最终会执行任务本身,而不仅仅是阻塞。
示例代码:
using System;
using System.Threading;
using System.Threading.Tasks;
class Test
{
static void Main()
{
// Make sure DemonstrateIssue is already called in a ThreadPool
// thread...
Task task = Task.Run((Action) DemonstrateIssue);
task.Wait();
}
static void DemonstrateIssue()
{
Console.WriteLine("DemonstrateIssue thread: {0}",
Thread.CurrentThread.ManagedThreadId);
Action action = () => Console.WriteLine("Inner task thread: {0}",
Thread.CurrentThread.ManagedThreadId);
Task task = new Task(action);
// Calling Start will just schedule it... we may be able to Wait
// before it actually executed
task.Start();
task.Wait();
}
}
每次运行时输出:
DemonstrateIssue thread: 3
Inner task thread: 3
这利用了以下事实:线程池不会根据需要立即启动线程 - 等待一段时间以查看现有线程在启动另一个线程之前是否可用。如果您在调用Thread.Sleep(5000);
之前添加task.Wait()
,则会看到这两项任务最终会出现在不同的主题上。