Task.Run(()=>{})
puts the action delegate into the queue and returns the task .
Is there any benefit of having async/await within the Task.Run()
?
I understand that Task.Run()
is required since if we want to use await directly, then the calling method will need to be made Async and will affect the calling places.
Here is the sample code which has async await within Task.Run()
. The full sample is provided here: Create pre-computed tasks.
Task.Run(async () => { await new WebClient().DownloadStringTaskAsync("");});
Alternatively this could have been done:
Task.Run(() => new WebClient().DownloadStringTaskAsync("").Result;);
Since both, Task.Run()
and Await will queue the work and will be picked by the thread pool, could the async/await within the Task.Run()
be a bit redundant?
Is there any benefit of having async/await within the Task.Run() ?
Yes. Task.Run
runs some action on a thread-pool thread. If such action does some IO work and asynchronously waits for the IO operation to complete via await
, then this thread-pool thread can be used by the system for other work while the IO operation is still running.
Example:
Task.Run( async () =>
{
DoSomeCPUIntensiveWork();
// While asynchronously waiting for this to complete,
// the thread is given back to the thread-pool
var io_result = await DoSomeIOOperation();
DoSomeOtherCPUIntensiveWork(io_result);
});
Is there any benefit of having async/await within the Task.Run()
An async method returns to the caller as soon as the first await is hit (that operates on a non-completed task). So if that first execution "streak" of an async method takes a long time Task.Run
will alter behavior: It will cause the method to immediately return and execute that first "streak" on the thread-pool.
This is useful in UI scenarios because that way you can make 100% sure that you are not blocking the UI. Example: HttpWebRequest
does DNS resolution synchronously even when you use one of the async methods (this is basically a library bug/design error). This can pause the UI thread. So you can use Task.Run to be 100% sure that the UI is never blocked for longer than a few microseconds.
So back to the original question: Why await inside a Task.Run body? For the same reason you normally await: To unblock the thread.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With