Основные причины для использования Function
, который возвращает Task
, а не Async Sub
, двояки.Первое - это обработка исключений.Если вы сделаете что-то подобное, вы получите неперехваченное исключение, которое прекратит работу вашего приложения:
Public Sub Main()
Try
DoSomethingAsync()
Catch ex As Exception
Console.WriteLine(ex)
End Try
End Sub
Private Async Sub DoSomethingAsync()
Throw New Exception()
End Sub
Исключение не будет перехвачено блоком Try / Catch, поскольку оно генерируется в отдельном потоке.
Однако, если вы сделаете это, он будет пойман и обработан:
Public Async Sub Main()
Try
Await DoSomethingAsync()
Catch ex As Exception
Console.WriteLine(ex)
End Try
End Sub
Private Async Function DoSomethingAsync() As Task
Throw New Exception()
End Sub
Вторая большая причина в том, что, хотя вам это может и не понадобиться сейчас, оно может вам понадобитьсяпотом.Если это уже функция, которая возвращает задачу, то вы можете использовать ее по своему усмотрению.Если вы этого не сделаете, вы не можете ожидать этого, или планировать события, которые будут происходить после него, или прерывать его, или делать любые другие вещи, которые вы можете делать с задачами.Таким образом, вопрос на самом деле не «зачем это делать?», А «почему бы не сделать это?»
Например, это выдает «Здесь», за которым следует «Готово»:
Public Sub Main()
DoSomethingAsync()
Threading.Thread.Sleep(5000)
Console.WriteLine("Done")
End Sub
Public Async Function DoSomethingAsync() As Task
Console.WriteLine("Here")
End Function
Как уже упоминалось, чтобы избежать предупреждения, вы можете назначить задачу переменной следующим образом:
Public Sub Main()
Dim t As Task = DoSomethingAsync()
Threading.Thread.Sleep(5000)
Console.WriteLine("Done")
End Sub
Она работает одинаково в любом случае и работает в своем собственном потоке, как Async Sub
.Не имеет значения, выходит ли переменная Task
из области видимости.Задача будет продолжаться, даже если на нее ничего не ссылается.Например:
Public Sub Main()
DoSomething()
Threading.Thread.Sleep(5000)
Console.WriteLine("Really Done")
End Sub
Public Sub DoSomething()
Dim t As Task = DoSomethingAsync()
Console.WriteLine("Done Doing Something")
End Sub
Public Async Function DoSomethingAsync() As Task
Console.WriteLine("Here")
End Function