Avviso del compilatore (livello 1) CS4014
Poiché la chiamata non può essere attesa, l'esecuzione del metodo corrente continua prima del completamento della chiamata.È possibile applicare l'operatore 'await' al risultato della chiamata.
Le chiamate al metodo correnti un metodo asincrono che restituisce Task o Task<TResult> e non implementa l'operatore di attendere al risultato.La chiamata al metodo async avvia un'attività asincrona.Tuttavia, poiché alcun operatore di await viene applicato, il programma procederà senza attendere l'attività.Nella maggior parte dei casi, tale comportamento non è quello previsto.Generalmente altri aspetti del metodo chiamante dipendono dai risultati della chiamata a, come minimo, il metodo chiamato si prevede di completare prima del completamento del metodo che contiene la chiamata.
Un'edizione ugualmente importante è quello che si verifica alle eccezioni generate nel metodo chiamato async.Un'eccezione generata in un metodo che restituisce Task o Task<TResult> viene archiviata nell'attività.Se non si attendono l'attività o in modo esplicito il controllo per le eccezioni, l'eccezione viene persa.Se si attendono l'attività, la relativa generata di nuovo.
Come procedura consigliata, è necessario attendere sempre la chiamata.
Considerare la possibilità di eliminare l'avviso solo se si è certi che non si desidera attendere la chiamata asincrona per completare e che il metodo chiamato non generare alcuna eccezione.In tal caso, è possibile eliminare l'avviso assegnare il risultato di attività della chiamata a una variabile.
Di seguito viene illustrato come generare l'avviso, come eliminarlo e come attendere la chiamata.
async Task CallingMethodAsync()
{
resultsTextBox.Text += "\r\n Entering calling method.";
// Variable delay is used to slow down the called method so that you can
// distinguish between awaiting and not awaiting in the program's output.
// You can adjust the value to produce the output that this topic shows
// after the code.
var delay = 5000;
// Call #1.
// Call an async method. Because you don't await it, its completion
// isn't coordinated with the current method, CallingMethodAsync.
// The following line causes warning CS4014.
CalledMethodAsync(delay);
// Call #2.
// To suppress the warning without awaiting, you can assign the
// returned task to a variable. The assignment doesn't change how
// the program runs. However, recommended practice is always to
// await a call to an async method.
// Replace Call #1 with the following line.
//Task delayTask = CalledMethodAsync(delay);
// Call #3
// To contrast with an awaited call, replace the unawaited call
// (Call #1 or Call #2) with the following awaited call. Best
// practice is to await the call.
//await CalledMethodAsync(delay);
// If the call to CalledMethodAsync isn't awaited, CallingMethodAsync
// continues to run and, in this example, finishes its work and returns
// to its caller.
resultsTextBox.Text += "\r\n Returning from calling method.";
}
async Task CalledMethodAsync(int howLong)
{
resultsTextBox.Text +=
"\r\n Entering called method, starting and awaiting Task.Delay.";
// Slow the process down a little so that you can distinguish between
// awaiting and not awaiting in the program's output. Adjust the value
// for howLong if necessary.
await Task.Delay(howLong);
resultsTextBox.Text +=
"\r\n Task.Delay is finished--returning from called method.";
}
Nell'esempio, se si sceglie la chiamata n o chiamate n, il termine unawaited di metodo async (CalledMethodAsync) dopo il relativo chiamante (CallingMethodAsync) che il chiamante del chiamante (startButton_Click) completi.L'ultima riga nell'output viene illustrato quando il metodo chiamato completa.La voce in e l'uscita dal gestore eventi che chiama CallingMethodAsync l'esempio completo sono contrassegnate nell'output.
Entering the Click event handler.
Entering calling method.
Entering called method, starting and awaiting Task.Delay.
Returning from calling method.
Exiting the Click event handler.
Task.Delay is finished--returning from called method.
È possibile eliminare gli avvisi del compilatore mediante le direttive #pragma warning (Riferimenti per C#).
Esempio
Nell'applicazione Windows Presentation Foundation (WPF) contiene i metodiesempio precedente.I passaggi seguenti si installa l'applicazione.
Creazione di un'applicazione WPF e denominarla AsyncWarning.
Nell'editor di codice di Visual Studio, scegliere la scheda MainWindow.xaml.
Se la scheda non è visibile, scegliere dal menu di scelta rapida per MainWindow.xaml in Esplora soluzionie quindi scegliere Visualizza codice.
Sostituire il codice nella visualizzazione XAML MainWindow.xaml con il codice seguente.
<Window x:Class="AsyncWarning.MainWindow" xmlns="https://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="https://schemas.microsoft.com/winfx/2006/xaml" Title="MainWindow" Height="350" Width="525"> <Grid> <Button x:Name="startButton" Content="Start" HorizontalAlignment="Left" Margin="214,28,0,0" VerticalAlignment="Top" Width="75" HorizontalContentAlignment="Center" FontWeight="Bold" FontFamily="Aharoni" Click="startButton_Click" /> <TextBox x:Name="resultsTextBox" Margin="0,80,0,0" TextWrapping="Wrap" FontFamily="Lucida Console"/> </Grid> </Window>
Una finestra semplice contenente un pulsante e una casella di testo visualizzato nella visualizzazione Progettazione MainWindow.xaml.
Per ulteriori informazioni sulla finestra di progettazione XAML, vedere Creazione di un'interfaccia utente tramite XAML Designer.Per informazioni su come compilare una semplice interfaccia utente, vedere "per creare un'applicazione WPF" e "progettare le sezioni di una Finestra WPF semplice di" Procedura dettagliata: accesso al Web tramite Async e Await (C# e Visual Basic).
Sostituire il codice nel file MainWindow.xaml.cs con il codice seguente.
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Windows; using System.Windows.Controls; using System.Windows.Data; using System.Windows.Documents; using System.Windows.Input; using System.Windows.Media; using System.Windows.Media.Imaging; using System.Windows.Navigation; using System.Windows.Shapes; namespace AsyncWarning { public partial class MainWindow : Window { public MainWindow() { InitializeComponent(); } private async void startButton_Click(object sender, RoutedEventArgs e) { resultsTextBox.Text += "\r\nEntering the Click event handler."; await CallingMethodAsync(); resultsTextBox.Text += "\r\nExiting the Click event handler."; } async Task CallingMethodAsync() { resultsTextBox.Text += "\r\n Entering calling method."; // Variable delay is used to slow down the called method so that you can // distinguish between awaiting and not awaiting in the program's output. // You can adjust the value to produce the output that this topic shows // after the code. var delay = 5000; // Call #1. // Call an async method. Because you don't await it, its completion // isn't coordinated with the current method, CallingMethodAsync. // The following line causes warning CS4014. CalledMethodAsync(delay); // Call #2. // To suppress the warning without awaiting, you can assign the // returned task to a variable. The assignment doesn't change how // the program runs. However, recommended practice is always to // await a call to an async method. // Replace Call #1 with the following line. //Task delayTask = CalledMethodAsync(delay); // Call #3 // To contrast with an awaited call, replace the unawaited call // (Call #1 or Call #2) with the following awaited call. Best // practice is to await the call. //await CalledMethodAsync(delay); // If the call to CalledMethodAsync isn't awaited, CallingMethodAsync // continues to run and, in this example, finishes its work and returns // to its caller. resultsTextBox.Text += "\r\n Returning from calling method."; } async Task CalledMethodAsync(int howLong) { resultsTextBox.Text += "\r\n Entering called method, starting and awaiting Task.Delay."; // Slow the process down a little so that you can distinguish between // awaiting and not awaiting in the program's output. Adjust the value // for howLong if necessary. await Task.Delay(howLong); resultsTextBox.Text += "\r\n Task.Delay is finished--returning from called method."; } } // Output with Call #1 or Call #2. (Wait for the last line to appear.) // Entering the Click event handler. // Entering calling method. // Entering called method, starting and awaiting Task.Delay. // Returning from calling method. // Exiting the Click event handler. // Task.Delay is finished--returning from called method. // Output with Call #3, which awaits the call to CalledMethodAsync. // Entering the Click event handler. // Entering calling method. // Entering called method, starting and awaiting Task.Delay. // Task.Delay is finished--returning from called method. // Returning from calling method. // Exiting the Click event handler. }
Premere il tasto F5 per eseguire il programma, quindi scegliere il pulsante Avvia.
L'output previsto viene visualizzato alla fine del codice.
Vedere anche
Riferimenti
Concetti
Programmazione asincrona con Async e Await (C# e Visual Basic)