.net线程安全
为什么锁定类型被认为是非常糟糕的?.net线程安全,.net,thread-safety,.net,Thread Safety,为什么锁定类型被认为是非常糟糕的? 例如,lock(typeof(DateTime))我知道.net中任何类的静态方法都被认为是线程安全的,而实例成员则不是。因此,在使用DateTime时没有必要锁定它。我正在读的这本书没有解释为什么它不好,只是说它不好。任何解释都很好。CLR为每个AppDomain维护每种类型的一个实例(正如Joe在回答中指出的,有时它们甚至在更广泛的上下文中共享) 由于您不控制对类型的访问,您可能会发现自己无意中被锁定在您的类型上的完全不相关的代码所阻止 相反,您通常应该锁
例如,
lock(typeof(DateTime))
我知道.net中任何类的静态方法都被认为是线程安全的,而实例成员则不是。因此,在使用DateTime时没有必要锁定它。我正在读的这本书没有解释为什么它不好,只是说它不好。任何解释都很好。CLR为每个AppDomain维护每种类型的一个实例(正如Joe在回答中指出的,有时它们甚至在更广泛的上下文中共享)
由于您不控制对类型的访问,您可能会发现自己无意中被锁定在您的类型上的完全不相关的代码所阻止
相反,您通常应该锁定与要锁定的操作(或相关操作)在同一类中的私有实例,以便可以控制锁定影响和阻止的内容。(尽管在某些情况下,锁定一些已知的同步对象是有意义的,这些对象将在不同的对象之间使用。)来自:
lock关键字通过获取给定对象的互斥锁,执行语句,然后释放锁,将语句块标记为关键部分。本声明采用以下形式:
所以基本上你应该锁定一个对象。因此,如果你想拥有一个锁,你应该拥有一个你正在锁定的特定对象,例如一个容器,比如一个专门用于锁定的哈希表
或一个共享对象
通过锁定
typeof(DateTime)
的结果,可以说明没有其他对象可以锁定该类型。这是一个过于粗粒度的锁定-换句话说,您的代码应该能够将另一个DateTime
对象锁定在代码中的其他位置,但是使用您的方法这是不可能的。除了前面提到的原因之外,一个类型对象可以在同一进程中的不同AppDomain之间共享。因此,在不同AppDomain中运行的代码可能会使应用程序死锁
对此有一些讨论。那么为什么允许这样做呢?是否真的需要这样做?因为你可以在.NET中锁定任何对象。为什么要为此添加额外的检查?