我有这段代码,我试图在并发字典中为一个键(键一直都是)更新项目(这是一个列表)。在更新ConcurrentDictionary中的元素时发生同步问题
这里是我的代码 - :
class Program
{
private static readonly ConcurrentDictionary<string, List<int>> s_mapDatatypeToSource = new ConcurrentDictionary<string, List<int>>();
static void Main(string[] args)
{
try
{
Parallel.For(0, 10000000, i => AddItemToList(i, "local"));
}
catch (Exception exception)
{
Console.WriteLine(string.Format("Exception thrown ...{0}", exception.Message));
Console.ReadLine();
throw;
}
Console.WriteLine("Completed without exception");
Console.ReadLine();
}
private static void AddItemToList(int dataKey, string sourceName)
{
s_mapDatatypeToSource.AddOrUpdate(sourceName.ToUpperInvariant(), new List<int> { dataKey }, (s, list) =>
{
{
list.Add(dataKey);
return list;
}
});
}
}
一个出上面的代码10次抛出异常 - “源阵列不够长检查SRCINDEX和长度,以及数组的下限。”
我知道这是一个同步问题的列表,但我不明白为什么会这样,因为ConcurrentDictionary是线程安全的。所以我认为,它可以让只有一个线程在同一时间来更新我的名单,所以不应该有任何problem-:
我知道我失去了一些东西 - 建议,请 - :
请以及格式化你的代码不可读 – 2014-12-03 06:40:49
GetOrAdd和AddOrUpdate不是原子(线程安全)的MSDN自己说: 此外,虽然ConcurrentDictionary的所有方法是线程安全的,并不是所有的方法都是原子的,特别是GetOrAdd和AddOrUpdate。传递给这些方法的用户委托在字典的内部锁之外被调用。 (这是为了防止未知代码阻塞所有线程。) – user3359453 2016-10-06 02:31:31