This question already has an answer here:
Is there any functional, performance, or risk of deadlock difference in the below code blocks?
Example 1:
await Task.WhenAll(task1, task2);
var result1 = await task1;
var result2 = await task2;
Example 2:
await Task.WhenAll(task1, task2);
var result1 = task1.Result;
var result2 = task2.Result;
Is there any functional, performance, or risk of deadlock difference in the below code blocks?
No, there isn't any such a case.
In both cases a task is created that will be completed when task1
and task2
would be completed.
Hence, when you write:
var result1 = await task1;
var result2 = await task2;
the code will be executed synchronoulsy. You don't have to await
for something, since you both task1
and task2
would have completed.
The same holds, for the second example, where you try to get their results.
var result1 = task1.Result;
var result2 = task2.Result;
Since, the tasks have already completed, you don't block any thread calling thread or having any context switch etc.
Update
The only functional difference that exists between these two approaches is that the error handling is different. The await
just unwraps an AggregateException
, while .Result
will just raise the exception.
await
will unwrap a AggregateException
where .Result
will just raise the exception intact. - Scott Chamberlain