Task.WaitAll不等待子任务完成?

5

你好,我有一个名为_noOfThreads的定义任务同时运行的变量。因此我使用%运算符继续进行任务,在循环结束时我使用Tasks.WaitAll。这是代码片段。

for (int index = 0; index < count; index++)
{

                if (index < _noOfThreads)
                    tasks[index] = Task.Factory.StartNew(somedelegate);
                else
                    tasks[index % _noOfThreads].ContinueWith(task => { foo.bar(); }, 
                            TaskContinuationOptions.AttachedToParent);
 }
  Task.WaitAll(tasks);

然而,我注意到它不会等待子任务完成。一旦父任务完成,Task.WaitAll 后面的下一行代码就会执行。我该如何修改这段代码以等待子任务完成?


可能是Task.ContinueWith not working how I expected的重复问题。 - mellamokb
顺便提一下,你似乎在决定任务调度。如果你想自定义调度,可以查看继承自 TaskScheduler 的内容。话虽如此,默认的调度程序已经做得很好了,在大量任务排队时不会过载系统线程。 - Dan Bryant
@Dan:那不是我的问题。我不想把这个交给TaskScheduler。我有一个变量,我只想启动和该变量数量相同的任务。简而言之,我想模拟Semaphore的行为方式,在那里你定义线程数量,只有那些线程可以同时进入某个代码片段。 - Tim Tom
2个回答

8
我认为你正在分配任务如下:

我认为你正在将你的任务分配为:

Tasks[] tasks = new Task[ _noOfThreads];

将您的代码更改为:

Tasks[] tasks = new Task[count];

for (int index = 0; index < count; index++)
{

    if (index < _noOfThreads)
         tasks[index] = Task.Factory.StartNew(somedelegate);
    else
         tasks[index] = tasks[index % _noOfThreads].ContinueWith(task => { foo.bar(); }, 
                            TaskContinuationOptions.AttachedToParent);
}
Task.WaitAll(tasks);

试一试吧!祝你好运 :)


3
你只需要等待原始任务完成。若要等待所有衍生任务完成,需在衍生任务上调用WaitAll。实现此目的的简单方法是将每个衍生任务重新分配给原始变量,这样你只需要等待最终的衍生任务。
else
    tasks[index % _noOfThreads] =
        tasks[index % _noOfThreads].ContinueWith(task => { foo.bar(); }, 
                        TaskContinuationOptions.AttachedToParent);

See also this related question.


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接