场景:循环中的异步任务执行一个方法,该方法包含随着程序的继续而改变的参数:
while(this._variable < 100)
{
this._variable++;
var aTask = Task.Factory.StartNew(() =>
{
aList.add(this._variable);
update(this._savePoint);
});
}
如果循环运行速度快于任务完成速度,列表会添加变量的当前值还是变量保存在本地并添加原始值?
最佳答案
闭包关闭变量,而不是值。因此,递增 _variable
可以改变引用它的任务的行为。
您可以通过制作本地副本来防止这种情况:
while (this._variable < 100)
{
this._variable++;
int local = _variable;
var aTask = Task.Factory.StartNew(() =>
{
aList.add(local);
update(this._savePoint);
});
}
或者您可以将值作为状态传递给任务:
while (this._variable < 100)
{
this._variable++;
var aTask = Task.Factory.StartNew(object state =>
{
aList.add((int)state);
update(this._savePoint);
}, this._variable);
}
它们都通过将 _variable
的值复制到一个新的临时变量来工作。在第一种情况下,local
变量是在循环范围内定义的,因此每次迭代都会得到一个新变量。在第二种情况下,当您将 _variable
的值作为 state
参数传递给任务时,您会复制它的值。如果 _variable
是引用类型,这些解决方案将不起作用;你必须执行克隆。
关于c# - 将具有变化值的参数传递给任务 - 行为?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10179691/