Код у вас как в порядке. Когда вы используете async
, компилятор уже реализовал всю необходимую сантехнику, чтобы вернуть задачу через сгенерированную реализацию IAsyncStateMachine
.
Как вы можете видеть в этом бессмысленном примере здесь
public async Task<bool> DoSomething()
{
return true;
}
переводит примерно на
[AsyncStateMachine(typeof(<DoSomething>d__0))]
public Task<bool> DoSomething()
{
<DoSomething>d__0 stateMachine = default(<DoSomething>d__0);
stateMachine.<>t__builder = AsyncTaskMethodBuilder<bool>.Create();
stateMachine.<>1__state = -1;
AsyncTaskMethodBuilder<bool> <>t__builder = stateMachine.<>t__builder;
<>t__builder.Start(ref stateMachine);
return stateMachine.<>t__builder.Task;
}
Вы бы использовали Task.FromResult
и Task.FromException
, если вы не добавили ключевое слово async
и выполняете синхронный код.
В этих случаях Task.FromResult
возвращает выполненное задание , и Task.FromException
добавит исключение к Заданию , как это сделает инфраструктура для исключения , брошенные async
методом
public Task<bool> DoSomeInterfaceAsync()
{
try
{
// return a completed task
return Task.FromResult(DoSomethingThatMightThrow());
}
catch (Exception e)
{
// Add the exception to the task
return Task.FromException<bool>(e);
}
}
Также интересно отметить, что в сгенерированном компилятором коде, показанном выше, есть метод MoveNext
, который подтверждает Task.FromResult
и Task.FromException
, и его можно увидеть ниже с SetException
и SetException
соответственно
private void MoveNext()
{
bool result;
try
{
result = true;
}
catch (Exception exception)
{
<>1__state = -2;
<>t__builder.SetException(exception);
return;
}
<>1__state = -2;
<>t__builder.SetResult(result);
}
AsyncTaskMethodBuilder.SetException
Помечает задачу как невыполненную и привязывает указанное исключение к
задача.
AsyncTaskMethodBuilder.SetResult
Помечает задачу как успешно выполненную.