关于多线程操作Dictionary,很简单的代码,却令人诧异
代码如下:
- C# code
Dictionary<int,int> dic=new Dictionary<int, int>(); void Button1Click(object sender, EventArgs e) { dic.Clear(); ThreadPool.QueueUserWorkItem(new WaitCallback(Method1),new object()); ThreadPool.QueueUserWorkItem(new WaitCallback(Method2),new object()); } void Method1(object o) { for (int i = 0; i < 50000; i++) { dic.Add(i,i); } Console.WriteLine("Method1 Count:"+dic.Count); } void Method2(object o) { for (int i = 50000; i < 100000; i++) { dic.Add(i,i); } Console.WriteLine("Method2 Count:"+dic.Count); }
两个线程往同一个Dictionary里添加元素,没有任何锁,两个线程一起往Dictionary中添加元素,所以第一个输出的数量应该是不确定的,但是第二个输出应该总是100000才对。但是实际运行时并不像想象时那样,第二个输出很少为100000。
之后我重写了Dictionary的Add方法,在Add方法中加了一个互斥锁,这个时候第一个输出的Count不确定,第二个输出就总是100000了,有哪位大牛能给解释一下吗?
[解决办法]
其实这个结果已经很明显了
最后字典中项目数不是1w,说明中间多线程同时访问的时候字典内部状态被破坏
至于破坏到哪种程度,这个就说不清楚了,除非大量测试或者研究源码。
有可能仅仅是某些项目被漏掉了;也有可能整个dictionary都已经处于一种损坏状态,所有后续操作都不可靠。
[解决办法]
典型的线程同步问题(产生的根本原因都类似),知道有这回事就行了。