Partilhar via


Operador Await (Visual Basic)

Você aplica o Await operador a um operando em um método assíncrono ou expressão lambda para suspender a execução do método até que a tarefa aguardada seja concluída. A tarefa representa um trabalho contínuo.

O método no qual Await é usado deve ter um modificador assíncrono . Tal método, definido usando o Async modificador, e geralmente contendo uma ou mais Await expressões, é referido como um método assíncrono.

Nota

As Async palavras-chave e Await foram introduzidas no Visual Studio 2012. Para obter uma introdução à programação assíncrona, consulte Programação assíncrona com Async e Await.

Normalmente, a tarefa à qual você aplica o Await operador é o valor de retorno de uma chamada para um método que implementa o padrão assíncrono baseado em tarefas, ou seja, um Task ou um Task<TResult>.

No código a seguir, o HttpClient método GetByteArrayAsync retorna getContentsTask, a Task(Of Byte()). A tarefa é uma promessa de produzir a matriz de bytes real quando a operação for concluída. O Await operador é solicitado a suspender a getContentsTask execução até SumPageSizesAsyncgetContentsTask que esteja concluída. Enquanto isso, o controle é retornado ao chamador de SumPageSizesAsync. Quando getContentsTask terminar, a Await expressão será avaliada como uma matriz de bytes.

Private Async Function SumPageSizesAsync() As Task

    ' To use the HttpClient type in desktop apps, you must include a using directive and add a
    ' reference for the System.Net.Http namespace.
    Dim client As HttpClient = New HttpClient()
    ' . . .
    Dim getContentsTask As Task(Of Byte()) = client.GetByteArrayAsync(url)
    Dim urlContents As Byte() = Await getContentsTask

    ' Equivalently, now that you see how it works, you can write the same thing in a single line.
    'Dim urlContents As Byte() = Await client.GetByteArrayAsync(url)
    ' . . .
End Function

Importante

Para obter o exemplo completo, consulte Passo a passo: acessando a Web usando Async e Await. Você pode baixar o exemplo do navegador de exemplo .NET. O código de exemplo está no projeto SerialAsyncExample .

Se Await for aplicado ao resultado de uma chamada de método que retorna um Task(Of TResult), o tipo da Await expressão é TResult. Se Await for aplicada ao resultado de uma chamada de método que retorna um Task, a Await expressão não retornará um valor. O exemplo a seguir ilustra a diferença.

' Await used with a method that returns a Task(Of TResult).
Dim result As TResult = Await AsyncMethodThatReturnsTaskTResult()

' Await used with a method that returns a Task.
Await AsyncMethodThatReturnsTask()

Uma Await expressão ou instrução não bloqueia o thread no qual está sendo executada. Em vez disso, ele faz com que o compilador inscreva o restante do método assíncrono, após a Await expressão, como uma continuação na tarefa esperada. Em seguida, o controle retorna ao chamador do método assíncrono. Quando a tarefa é concluída, ela invoca sua continuação e a execução do método assíncrono é retomada de onde parou.

Uma Await expressão pode ocorrer somente no corpo de um método imediatamente fechado ou expressão lambda marcada por um Async modificador. O termo Await serve como palavra-chave apenas nesse contexto. Em outros lugares, é interpretado como um identificador. Dentro do Async método ou expressão lambda, uma Await expressão não pode ocorrer em uma expressão de consulta, no Catch bloco ou Finally de um Try... Pegar... Finalmente, na expressão da variável de controle de loop de um For ou For Each loop, ou no corpo de uma instrução SyncLock .

Exceções

A maioria dos métodos assíncronos retorna um Task ou Task<TResult>. As propriedades da tarefa retornada carregam informações sobre seu status e histórico, como se a tarefa foi concluída, se o método assíncrono causou uma exceção ou foi cancelado e qual é o resultado final. O Await operador acessa essas propriedades.

Se você aguardar um método assíncrono de retorno de tarefa que cause uma exceção, o Await operador relançará a exceção.

Se você aguardar um método assíncrono de retorno de tarefa que seja cancelado, o Await operador relançará um OperationCanceledExceptionarquivo .

Uma única tarefa que está em um estado de falha pode refletir várias exceções. Por exemplo, a tarefa pode ser o resultado de uma chamada para Task.WhenAll. Quando você aguarda tal tarefa, a operação await relança apenas uma das exceções. No entanto, você não pode prever qual das exceções será relançada.

Para obter exemplos de tratamento de erros em métodos assíncronos, consulte Tentar... Pegar... Finalmente Declaração.

Exemplo

O exemplo de Windows Forms a seguir ilustra o uso de Await em um método assíncrono, WaitAsynchronouslyAsync. Compare o comportamento desse método com o comportamento de WaitSynchronously. Sem um Await operador, é executado de forma síncronaAsync, WaitSynchronously apesar do uso do modificador em sua definição e uma chamada para Thread.Sleep em seu corpo.

Private Async Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
    ' Call the method that runs asynchronously.
    Dim result As String = Await WaitAsynchronouslyAsync()

    ' Call the method that runs synchronously.
    'Dim result As String = Await WaitSynchronously()

    ' Display the result.
    TextBox1.Text &= result
End Sub

' The following method runs asynchronously. The UI thread is not
' blocked during the delay. You can move or resize the Form1 window
' while Task.Delay is running.
Public Async Function WaitAsynchronouslyAsync() As Task(Of String)
    Await Task.Delay(10000)
    Return "Finished"
End Function

' The following method runs synchronously, despite the use of Async.
' You cannot move or resize the Form1 window while Thread.Sleep
' is running because the UI thread is blocked.
Public Async Function WaitSynchronously() As Task(Of String)
    ' Import System.Threading for the Sleep method.
    Thread.Sleep(10000)
    Return "Finished"
End Function

Consulte também