There is a Task variable and lets say the task is running right now.. by executing the following line.
await _task;
I was wondering what happens when I write this code:
await _task;
await _task;
would it execute the task twice ? Or throw an exception because it has already run ?
I threw together this quick test:
It writes:
So, clearly, the task only runs once.
No and no. The only thing
await
does is callTask.GetAwaiter
, it does not cause anything to run. If the task already ran to completion, it will either extract the value if it is aTask<T>
, or run synchronously to the next line if it is aTask
, since there is an optimization for already completed tasks.A simple demo:
If you drill down to the state machine itself, you'll see this:
This optimization first checks the completion of the task. If the task isn't complete, it will call
UnsafeOnCompleted
which will register the continuation. If it is complete, it breaks theswitch
and goes to:Which sets the result for the underlying
Task
, and that way you actually get the value synchronously.