My problem is that when a Task has a Task.WhenAll() call (running other Tasks) the line of WhenAll() makes the consuming code continue execution, unlike what I would expect. So the following code outputs “finished” immediately when the Task.WhenAll() is hit, not after all the tasks in its argument are finished.
// Just a simple async method
public Task DoWorkAsync()
{
return Task.Factory.StartNew(
() =>
{
// Working
});
}
// This one used the previous one with Task.WhenAll()
public Task DoLoadsOfWorkAsync()
{
return Task.Factory.StartNew(
async () =>
{
// Working
// This line makes the task return immediately
await Task.WhenAll(DoWorkAsync(), DoWorkAsync());
// Working
});
}
// Consuming code
await DoLoadsOfWorkAsync();
Console.WriteLine("finished");
I’d expect the WriteLine() to be called when the last line of DoLoadsOfWorkAsync() is executed.
What am I doing wrong? Thanks in advance.
Task.WhenAllreturns a newTaskimmediately, it does not block. The returned task will complete when all tasks passed toWhenAllhave completed.It is an asynchronous equivalent to
Task.WaitAll, and this is the method to use if you want to block.However you have another problem. Using
Task.Factory.StartNewand passing anasyncdelegate seems to lead to a type ofTask<Task>where the outer task completes when the inner task starts to execute (rather than when it has completed).Using the newer
Task.Runavoids this.