Bit*_*lue 3 c# multithreading locking
我正在为多个项目编写一个库.它包含包含和操作数据的类.所以我认为我应该在执行这些类的方法时锁定这些数据.但我还想过,如果必须完成线程安全的数据操作,那么让更高的应用程序层处理锁定.稍后实际应用程序使用类库的最佳实践是什么.
假设我有一堂课SpecialList.我该怎么办:
?
如果我知道.NET Framework类如何List处理,我会做同样的事情.
如果您正在设计需要保证线程安全的数据结构和类型,那么请确保将锁和其他构造放入这些类型中以维护这些保证.
但是,单靠锁是不够的.
拿一本简单的字典.假设您要确保字典内的内部数据结构不会被多个线程损坏,因此您需要引入锁.但是,如果外部代码执行此操作:
if (!dict.ContainsKey(key))
dict.Add(key, value);
Run Code Online (Sandbox Code Playgroud)
然后就不能保证在调用ContainsKey和之间Add,某些其他线程还没有将该键添加到字典中.
因此,线程安全类型可能需要比简单锁定更多的东西.可能需要一种方法,可以安全地将键和值添加到字典(如果它尚未存在),在原子操作中,然后返回一个标志,告诉您它做了什么.
实际上,请看这里:ConcurrentDictionary.TryAdd.
我的建议是这样的:
.NET类型List不以任何方式使用锁,除了一些关注线程安全的选择位置,特别是SyncRoot属性.
此外,编写好的线程安全数据类型并不容易.只需在你需要的地方放入锁就可能使它更安全,但你会在性能方面付出沉重的代价.如果一个程序在使用它时不需要它是线程安全的,你仍然需要支付很多这个价格.
编写高性能的线程安全类型更难,并且通常不依赖于锁(单独),而是使用旋转等待,特定CPU指令(其中一些可用于.NET代码)等等.但这需要高度关于现代CPU如何执行代码的专业知识.
如果我是你,我会给专家留下线程安全,并从你自己的类型中删除它,除非你绝对需要它.