Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

On async return type

Wondering why we should specify that async method does return Task object.

Specifying it seems redundant with the async keyword plus it is confusion since you do not really create the Task object.

As I understand the compiler does emit the necessary code for Task object creation (Whether on a await call or wrapping the return with a new Task.).

I don't really like the inconsistency between the declare type and the return Type.

like image 775
mathk Avatar asked Feb 23 '26 12:02

mathk


1 Answers

This isn't really a question: it's more of a rant and therefore not particularly suitable for StackOverflow:

I don't really like the inconsistency between the declare type and the return type.

If you want to complain, start a blog and complain on that. Let's reformulate that as a question:

The declared type returned by an async method might be, say Task<int> but the expression returned by a return statement in that method must be implicitly convertible to int, not Task<int>. This is potentially confusing. What design principle justifies this behaviour?

You are right that this is potentially confusing. It is confusing because async methods separate two things that we are very used to thinking of as one thing. Those two things are:

  • What type of object is returned when control resumes in the caller of this method?
  • What type of object is passed from the method to its continuation? Remember that the continuation of a method is the code that runs when the method completes.

In synchronous methods those two things are always the same because the point of resumption in the caller is the continuation of a synchronous method. But the whole point of an asynchronous method is that the code in the caller is not the continuation of the method. The continuation of the method is controlled by setting the continuation of the task associated with it.

That's why the declared return type and the type given to the return statement are different. The caller wants a Task<int> but the continuation of the method wants an int. The return statement means "this method is done; give this value to my continuation" regardless of whether the method is synchronous or asynchronous.

like image 73
Eric Lippert Avatar answered Feb 26 '26 02:02

Eric Lippert



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!