初始化并发包是否可以安全?

时间:2013-07-12 22:09:15

标签: c# multithreading concurrency

我有一位作家和多个并发包的读者。

作者定期从数据库刷新concurrentbag的完整内容。

在编写器线程中重新初始化(即= new concurrentbag)是否安全?如果没有,我看到唯一的选择是在所有读取和写入期间将其锁定,而不是取消这一点。我不能在袋子上迭代一次清空一块,因为任何读取粪便的过程都会根据部分信息将其行为作为基础。

谢谢大家!

1 个答案:

答案 0 :(得分:1)

首先,这与ConcurrentBag类型无关。就此而言,它本身就是完全安全的。

如果在一个线程上正在对包执行方法调用,而在另一个线程上同时执行此操作:

_BagField = new ConcurrentBag<string>();

然后第一个线程上的方法调用就会很好,但旧实例上的

但是,并不安全,但由于首先使用该类型的原因,从未

if (_BagField.Any())
    var percentage = 100 / _BagField.Count(); // broken

这可能在一个实例上调用.Any(),在另一个实例上调用.Count(),但这从来都不安全,因为没有安全措施可以确保在调用之后Count不会降到零Any

但请注意,您无法保证其他线程会立即获取新实例。

例如,这个:

string temp;
while (!_Bag.TryTake(out temp))
{
    // process temp
}

可能永远不会到达新实例,并会在停止死亡之前继续处理旧的包实例。

为确保这一点,请确保包含行李引用的字段为volatile