Une conversion implicite se produit-elle entre Task <> et int?
Nan. C'est juste une partie de la façon dont async/ awaitfonctionne.
Toute méthode déclarée comme asyncdoit avoir un type de retour de:
void (éviter si possible)
Task (aucun résultat au-delà de la notification d'achèvement / d'échec)
Task<T>(pour un résultat logique de type Tde manière asynchrone)
Le compilateur effectue tout l'encapsulation appropriée. Le fait est que vous retournez de manière asynchroneurlContents.Length - vous ne pouvez pas simplement renvoyer la méthode int, car la méthode réelle retournera lorsqu'elle atteindra la première awaitexpression qui n'est pas déjà terminée. Donc, à la place, il retourne un Task<int>qui se terminera lorsque la méthode async elle-même sera terminée.
Notez que cela awaitfait le contraire - il déroule a Task<T>en une Tvaleur, c'est ainsi que cette ligne fonctionne:
string urlContents = await getStringTask;
... mais bien sûr, il le déballe de manière asynchrone, alors que le simple fait d'utiliser Resultle bloquerait jusqu'à ce que la tâche soit terminée. ( awaitpeut dérouler d'autres types qui implémentent le modèle attendu, mais Task<T>c'est celui que vous utiliserez probablement le plus souvent.)
Ce double emballage / déballage est ce qui permet à async d'être aussi composable. Par exemple, je pourrais écrire une autre méthode asynchrone qui appelle la vôtre et double le résultat:
public async Task<int> AccessTheWebAndDoubleAsync()
{
var task = AccessTheWebAsync();
int result = await task;
return result * 2;
}
(Ou tout simplement return await AccessTheWebAsync() * 2;bien sûr.)
asyncmot clé.