Attendere vs Task.Wait – Deadlock?

Non capisco la differenza tra Task.Wait e await .

Ho qualcosa di simile alle seguenti funzioni in un servizio WebAPI di ASP.NET:

 public class TestController : ApiController { public static async Task Foo() { await Task.Delay(1).ConfigureAwait(false); return ""; } public async static Task Bar() { return await Foo(); } public async static Task Ros() { return await Bar(); } // GET api/test public IEnumerable Get() { Task.WaitAll(Enumerable.Range(0, 10).Select(x => Ros()).ToArray()); return new string[] { "value1", "value2" }; // This will never execute } } 

Dove arriverà lo stallo.

Cosa potrebbe causare questo? Perché questo non causa un problema quando utilizzo un’attesa di blocco piuttosto che await Task.Delay ?

Wait e await – mentre sono concettualmente simili – sono in realtà completamente diversi.

Wait verrà Wait modo sincrono fino al completamento dell’attività. Quindi il thread corrente viene letteralmente bloccato in attesa del completamento dell’attività. Come regola generale, dovresti usare ” async fino in fondo”; cioè, non bloccare il codice async . Nel mio blog, passo nei dettagli su come il blocco del codice asincrono causi un deadlock .

await in modo asincrono fino al completamento dell’attività. Ciò significa che il metodo corrente è “sospeso” (il suo stato è catturato) e il metodo restituisce un’attività incompleta al chiamante. Successivamente, quando l’espressione await completa, il resto del metodo viene pianificato come una continuazione.

Hai anche menzionato un “blocco cooperativo”, in base al quale presumo tu intenda che un’attività che stai aspettando possa eseguire sul thread in attesa. Ci sono situazioni in cui ciò può accadere, ma è un’ottimizzazione. Esistono molte situazioni in cui non può accadere, ad esempio se l’attività è per un altro programma di pianificazione o se è già stata avviata o se è un’attività non di codice (ad esempio nell’esempio di codice: Wait non può eseguire l’attività Delay linea perché non c’è nessun codice per questo).

Puoi trovare utile la mia async / await .