【问题标题】:Why ConcurrentDictionary<decimal,...>.tryAdd modify the order of item in the dictionnary ? c# [duplicate]为什么 ConcurrentDictionary<decimal,...>.tryAdd 修改字典中项的顺序? c# [重复]
【发布时间】:2019-01-24 17:18:15
【问题描述】:

我在字典中添加四个元素,并使用 ForEach 循环遍历字典:项目按添加顺序。

我在 ConcurentDictionary 中添加四个元素,并使用 ForEach 循环遍历 ConcurentDictionnary:项目按添加顺序NOT

为什么?

    static void Main(string[] args)
    {

        Console.WriteLine("Add four items to dictionnary");
        var d = new Dictionary<decimal, int>();

        d.Add(1.05m, 1);
        d.Add(2.3m, 2);
        d.Add(1.3m, 3);
        d.Add(4m, 4);

        Console.WriteLine("iterate trough Dictionnary");
        foreach (var x in d) Console.WriteLine($"{x.Key:0.000} {x.Value}");

        Console.WriteLine("\r\nAdd four items to ConcurrentDictionary");
        var cd = new ConcurrentDictionary<decimal,int>();

        cd.TryAdd(1.05m, 1);
        cd.TryAdd(2.3m, 2);
        cd.TryAdd(1.3m, 3);
        cd.TryAdd(4m, 4);

        Console.WriteLine("iterate trough  ConcurrentDictionary");
        foreach (var x in cd) Console.WriteLine($"{x.Key:0.000} {x.Value}");

        Console.WriteLine("\r\niterate trough  Keys");
        foreach (var x in cd.Keys) Console.WriteLine($"{x:0.000}");

        Console.WriteLine("\r\niterate trough  Keys");
        foreach (var x in cd.Values) Console.WriteLine($"{x}");

        Console.ReadKey();
    }

结果

在字典中添加四个项目 遍历字典
1.050 1
2.300 2
1.300 3
4.000 4

向 ConcurrentDictionary 添加四个项目
遍历 ConcurrentDictionary
4.000 4
2.300 2
1.300 3
1.050 1

迭代槽键
4.000
2.300
1.300
1.050

迭代谷值
4
2
3
1

edit :测试表明,即使文档中没有保证顺序,实际上也是如此。

我阅读了 ConcurrentDictionary.cs 中的源代码,发现为什么 ConcurrentDictionary 与 Dictionary 不同。

我尝试写一个回复(我是法国人和初学者写一个关于stackoverflow的问题)

【问题讨论】:

  • 字典是无序的。
  • 哼,我的问题不能再添加答案了吗?
  • 其实,看完这里的源码:referencesource.microsoft.comConcurrentDictionnary分析key的类型用: IsValueWriteAtomic() - 如果key可以用原子的方式写,ConcurrentDictionnay用一张表来存储键/值对。在这种情况下,值是按相加的顺序存储的。 - 如果key不能随意写入,ConcurrentDictionary使用链表来存储key/value对。在这种情况下,存储顺序与添加顺序无关。

标签: c# concurrentdictionary


【解决方案1】:

Dictionary (https://docs.microsoft.com/en-us/dotnet/api/system.collections.generic.dictionary-2) 的 MSDN 文档指出

物品的返回顺序未定义

虽然ConcurrentDictionary 的文档没有这样说(https://docs.microsoft.com/en-us/dotnet/api/system.collections.concurrent.concurrentdictionary-2),但同样如此。这个问题 Is the list order of a ConcurrentDictionary guaranteed? 也说明了这种情况。

如果你想要一个排序字典,有一个 SortedDictionary 类,但它不是 Concurrent - 如果你想要这个,你必须自己编写,或者为你的代码使用不同的方法。

【讨论】:

  • 好吧,奇怪的是,在我的测试中,问题只出现在 CnncurrentDictionnary 上,键为十进制 ...
猜你喜欢
  • 2018-06-13
  • 2016-11-18
  • 2013-01-04
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多