web-dev-qa-db-fra.com

Comment obtenir le résultat booléen de la fonction <bool> de tâche asynchrone en C # - Erreur: Impossible de convertir implicitement le type `void 'en` bool'

J'ai créé une fonction de tâche pour valider mon fichier json. Tout fonctionne bien jusqu'à ce que je n'utilise pas le résultat. Lorsque j'essaie d'obtenir le résultat de async task<bool> function il affiche une erreur sous la forme Cannot implicitly convert 'void' to bool. Ma fonction asynchrone est la suivante:

 private async Task<bool> MyValidationFunction(string json)
 {
     bool isValid = true;
     .......DOING MY VALIDATION STUFF.....
     return isValid;
 }

L'appel de cette fonction à partir d'une autre fonction est le suivant:

 public bool GetJsonAndValidate()
 {
      bool isValid = true;
      string jsonData = GetJson();
      //******* Here I am getting the error.
      bool isValid = MyValidationFunction(jsonData).Wait(); 
 }

Lorsque j'essaie d'appeler MyValidationFunction, il affiche l'erreur comme mentionné ci-dessus. J'ai essayé d'obtenir un résultat en utilisant la propriété Result mais c'est un lancer et une erreur. Ma classe est juste une classe publique simple. Je peux le faire avec un appel synchrone mais j'ai besoin d'un appel asynchrone car MyValidationFunction obtient le résultat de la base de données. Si je n'ai pas utilisé la variable bool pour capturer le résultat, cela fonctionne très bien. Qu'est-ce que j'ai raté? Comment puis-je obtenir le résultat booléen de ma fonction de validation?

11
Iswar

Instruction 1. .Wait() n'a pas de résultat de retour. C'est une méthode void, et donc son résultat ne peut pas être assigné à une variable.
Vous pouvez utiliser .Result qui attendra que Task se termine et renvoie un résultat.

// Both are applicable to simple Tasks:
bool isValid = MyValidationFunction(jsonData).Result;

// does that same as

var task = MyValidationFunction(jsonData);
task.Wait();  
bool isValid = task.Result;

Cependant, tout cela est valable pour les tâches habituelles, mais pas pour la fonctionnalité asynchrone/attente , car ...

Instruction 2. Ne mélangez pas asynchrone et .Wait() - cela bloque toujours le thread, tuant le idée asynchrone/attendre et annuler toute amélioration des performances.

Il provoque également un blocage dans WinForms, WPF, ASP.NET et d'autres environnements avec SynchronizationContext. Pour en savoir plus à ce sujet article de Stephen Cleary ou dans ces questions sur StackOverflow:

Règle simple: si vous utilisez async, vous utilisez alors wait .

// That's how you do it with async/await:
public async bool GetJsonAndValidate()
{
     string jsonData = GetJson();
     bool isValid = await MyValidationFunction(jsonData); 
}

Il ne bloquera pas le thread et activera le comportement asynchrone.

30

Change ça:

bool isValid = MyValidationFunction(jsonData).Wait(); 

à

  bool isValid = MyValidationFunction(jsonData).Result; 

Task.Wait's le type de retour est void. Task.Result fait une attente et récupère le résultat de la tâche.

Pas lié à la question d'OP, mais sa mauvaise idée de mélanger async et Wait (ou Result). Vous pouvez obtenir des blocages étranges dans votre application en raison de blocages si votre application dépend d'un SynchronizationContext

4
bashrc

J'ai travaillé avec des méthodes asynchrones et je l'ai toujours utilisé de cette façon:

bool isValid = await MyValidationFunction(jsonData);

J'ai vu les réponses fournies.

Parfois, le résultat meurt. Donc, je vous suggère d'utiliser Wait au lieu de .Result.

0
Bob Swager