[英]Using ConcurrentBag correctly
编辑:谢谢,您让我意识到下面的代码无法正常运行,因为我以某种方式认为cbag像哈希集一样工作。 抱歉,您为我省了很多麻烦:)
以下函数是唯一可以更改_currentSetOfStepsProcessing的函数。 可以从不同的线程调用此函数。 我不确定我是否正确理解ConcurrentBag的用法,因此请让我知道您认为这是否可行。 一旦流程开始,就不会修改_stepsToDo数据结构。
void OnStepDone(InitialiseNewUserBase obj)
{
var stepToDo = _stepsToDo[_currentSetOfStepsProcessing];
stepToDo.TryTake(out obj);
if (stepToDo.Count == 0) //can I assume it will enter here once per ConcurrentBag?
{
if (_currentSetOfStepsProcessing < _stepsToDo.Count - 1)
{
_currentSetOfStepsProcessing++;
}
}
}
List<ConcurrentBag<InitialiseNewUserBase>> _stepsToDo = new List<ConcurrentBag<InitialiseNewUserBase>>();
Action _onFinish;
int _currentSetOfStepsProcessing;
stepToDo.TryTake(out obj);
可能会失败,您将无法处理。 out
引用方法参数? 这只会覆盖参数。 如果把它丢掉,为什么还要争论呢? 这很可能是某种误解。 can I assume it will enter here once per ConcurrentBag
因为对包的访问显然是并发的,多个访问线程可能会看到0
。 所以是的,您需要更好地处理这种情况。 可能,您不应使事情变得如此困难,而应将lock
与非并发数据结构结合使用。 只有在似乎不太可能进行频繁的制袋操作时,这才是一个好主意。
那这个呢:
foreach (/*processing step*/) {
Parallel.ForEach(/*item in the step*/, x => { ... });
}
简单得多。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.