比方说,我有一个表单,里面有一段数据,需要用在await'ed方法中。
using (var riskForm = new RiskValidationForm(config))
{
if (riskForm.OpenDialog() == DialogResult.Cancel)
return;
await Task.Run(() => MyMethod(riskForm.GetRiskData());
}
这样做危险吗?我担心表单可能会在 await 方法开始之前处理掉 RiskData() 返回的数据。因此,我将在已经被处理掉的东西上调用RiskData()。这可能吗?
MyMethod的函数签名。
private void MyMethod(RiskLimitsConfigurationCollection riskLimits)
不,这不可能是 Form
将在完成前进行处置。Task
. 该 await
里面 using
声明确保。但即使你删除了 using
await
组合(使任务本质上是fire-and-forget),仍然不会有问题。垃圾回收器不会回收还在使用中的对象。在 Task
将持有对 闭合 的引用,将持有对 RiskValidationForm
和 Task
对象 在其完成之前不回收 除非申请被终止)。
不过你还有两个原因需要担心。
MyMethod
方法,它可以被多个线程并发调用。它可以被多个线程同时调用,除非有UI代码阻止它发生(例如禁用激活的 Button
而任务仍在运行)。) GetRiskData
方法的任何方法或属性。如果这个方法访问了任何UI控件的任何方法或属性,那么这个方法就会访问 RiskValidationForm
表,你已经犯了 跨线程违规 因为你从UI线程以外的线程访问了一个UI元素。