2012-01-06 72 views
3

我是SyncRoot概念的新手。据我所知,用于锁定的对象应该是私有的。SyncRoot对象是否真的线程安全?

但是HashTable有一个公共属性,SyncRoot,它只是一个私人SyncRoot对象的包装。枚举集合时,您锁定HashTable.SyncRoot的是recommended

看起来我们可能因为死锁而失败,因为它不再是私人的。它真的是线程安全的吗?

如果我使自己的私人锁定机制呢? private readonly object _syncObject;

哪一个更好?为什么?

+0

你能告诉我任何可以使用它的场景吗?因为我觉得SyncRoot属性只是一个包装,因此是线程安全漏洞。 – 2012-01-06 12:21:20

回答

5

不,这不是.NET 1.x方法的真正问题。该物业是公开的,因为它可公开访问。枚举集合的麻烦是。没有办法以线程安全的方式实现这一点,当你完成枚举和解锁时,没有任何机制可以自动锁定。 IEnumerable没有Completed方法,不会继承IDisposable。

所以允许代码安全枚举,您需要访问锁定对象。所以你可以用对该对象的锁来包装foreach语句。因此公共SyncRoot属性。

然而,许多程序员陷入的最大熊陷阱是假设没有必要。购买Synchronized属性为所有情况下都是线程安全的集合返回线程安全包装的概念。事实并非如此。

5

ICollection.SyncRoot只在预通用集合上。它基本上已经过时了。

由于您提到的原因,这在泛型集合中被删除 - 您应该使用自己的锁定机制来控制对具有您需要的属性(保持锁定私人,避免死锁...)的集合的访问,比使用SyncRoot对象,然后假设你的代码是神奇的线程安全的。

+0

kool ...感谢您澄清我的疑问。 – 2012-01-06 12:23:33

+0

@DJ如果它的权利标记为正确... – RhysW 2012-05-10 07:43:28