在Windows Phone 7 / Silverlight中,以下代码是安全的还是竞争条件?
//Snippet 1
foreach(var item in list)
{
Deployment.Current.Dispatcher.BeginInvoke( () => { foo(item); });
}
肯定(?)这个替代方案很活泼?
//Snippet 2
Deployment.Current.Dispatcher.BeginInvoke( () =>
{
foreach(var item in list){ foo(item); }
});
list.Clear();
答案 0 :(得分:6)
“竞争条件”可能不是解决第一个代码段问题的最佳方法。但基本上,您在捕获范围之外使用捕获的变量。对于所有项目,“item”的值最终将成为最后一项,然后调用foo
方法。
相反,这样做:
foreach(var item in list)
{
var tmpItem = item;
Deployment.Current.Dispatcher.BeginInvoke( () => foo(tmpItem));
}
这会将变量放在较低的范围内,并在该范围内捕获。这样可以确保捕获每个值并将其发送到foo
。
考虑到list
变量的合理范围,第二个版本几乎肯定是一个错误。