.Net支持对过程或函数进行异步调用,通过将目标过程或函数封装为对象,可以实现参数和结果的双向传递。
下例中,控制器类OperationController位于主线程中,通过DoWorkAsync()函数控制工作线程Worker的实例WorkerInstance执行一耗时操作(在Worker.DoWork()中实现)。工作开始时,传入Param1(Param1Type类型)和Param2(Param2Type类型)两个参数,并接收类型为ResultType的返回结果。
Imports System.Threading.Tasks
'Controller class
Public Class OperationController
'Worker thread
Private Class Worker
'Input parameters
Private _Param1 As Param1Type
Private _Param2 As Param2Type
'Return values
Private _Result As ResultType
'Constructor
Public Sub New(Optional NewParam1 As Param1Type = Nothing, Optional NewParam2 As Param2Type = Nothing)
_Param1 = NewParam1
_Param2 = NewParam2
End Sub
'Work content
Public Function DoWork() As ResultType
'Do work here
'...
'...
'Set results
_Result = New ResultType()
Return _Result
End Function
'Param1 property
Public Property Param1 As Param1Type
Get
Return _Param1
End Get
Set(value as Param1Type)
_Param1 = value
End Set
End Property
'Param2 property
Public Property Param2 As Param2Type
Get
Return _Param2
End Get
Set(value as Param2Type)
_Param2 = value
End Set
End Property
'Result property
Public ReadOnly Property Result As ResultType
Get
Return _Result
End Get
End Property
End Class
'Call worker asynchronously
Public Async Function DoWorkAsync(Param1 As Param1Type, Param2 As Param2Type) As Task(Of ResultType)
'Initialize worker instance
Dim WorkerInstance As New Worker(Param1, Param2)
'Run work in a separated thread
Await Task.Factory.StartNew(Sub()
WorkerInstance.DoWork()
End Sub)
'Return result
Return WorkerInstance.Result
End Function
'Call worker asynchronously, no return values
Public Async Function DoWorkAsyncNoReturnValue(Param1 As Param1Type, Param2 As Param2Type) As Task
'Initialize worker instance
Dim WorkerInstance As New Worker(Param1, Param2)
'Run work in a separated thread
Await Task.Factory.StartNew(Sub()
WorkerInstance.DoWork()
End Sub)
End Function
End Class
从外部调用时:
Private Async Sub AsyncSubDemo()
Dim ControllerInstance As New OperationController
Dim WorkResult As ResultType
'With result
WorkResult = await ControllerInstance.DoWorkAsync()
'Without result
await ControllerInstance.DoWorkAsyncNoReturnValue()
End Sub
若您正在使用.Net Framework 4.0,那么您需要在项目中引用Microsoft.Bcl和Microsoft.Bcl.Async等2个程序集,方能正常使用Await关键字。否则会提示“找不到“async”修饰符所需的所有类型。是否面向了错误的框架版本,或缺少对程序集的引用?”错误。您还需要在App.config文件的@configuration@节中的@runtime@节(您可能需要手动加入@runtime></runtime@节)内添加assemblyBinding重定向:
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
<dependentAssembly>
<assemblyIdentity name="System.Runtime" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.6.8.0" newVersion="2.6.8.0" />
</dependentAssembly>
<dependentAssembly>
<assemblyIdentity name="System.Threading.Tasks" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-2.6.8.0" newVersion="2.6.8.0" />
</dependentAssembly>
</assemblyBinding>
参考资料:
https://www.cnblogs.com/yilezhu/p/10555849.html
https://learn.microsoft.com/en-us/answers/questions/1147105/microsoft-bcl-package-dependency-issue
https://www.cnblogs.com/xishuai/p/entityframework_async_await_SaveChangesAsync_ToListAsync.html