Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/315.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 字典的行为就像一个有序的集合_C#_Dictionary - Fatal编程技术网

C# 字典的行为就像一个有序的集合

C# 字典的行为就像一个有序的集合,c#,dictionary,C#,Dictionary,我读到过关于字典类型的文章,说它不是有序集合(因为它是KVP)。但我有以下代码: var dictionary = new Dictionary<Func<bool>, string> { { () => true, "first" }, { () => true, "second" } }; for (var i = 0; i < 40;

我读到过关于
字典
类型的文章,说它不是有序集合(因为它是KVP)。但我有以下代码:

        var dictionary = new Dictionary<Func<bool>, string>
        {
            { () => true, "first" },
            { () => true, "second" }
        };

        for (var i = 0; i < 40; i++)
        {
            Console.WriteLine(dictionary.First(f => f.Key()).Value);
        }
var字典=新字典
{
{()=>true,“第一”},
{()=>true,“第二个”}
};
对于(变量i=0;i<40;i++)
{
Console.WriteLine(dictionary.First(f=>f.Key()).Value);
}
上面的代码只打印字符串“first”。如果集合未订购,为什么不打印“second”字符串?

为什么要打印“second”?
First
返回一个且唯一一个满足条件的元素

它在内部循环遍历所有元素(我假设未指定顺序),并在满足条件时停止

因此在您的例子中,
()=>true,“first”
对恰好是第一个被测试的。它返回true,因此返回


显示枚举顺序(很可能与第一个测试条件的顺序相同):正如其他人所指出的,以及MSDN中所述,此顺序未定义:它是一个可以在.Net framework的未来版本中更改的实现细节,使用
KeyValuePair
并不是
字典
无序的原因。
SortedDictionary
也使用
KeyValuePair
,但由于该对被实现为一个平衡的黑-红二叉树而被排序。
字典
实现为哈希映射。因此,顺序取决于键
对象
生成的哈希值和桶数。在您的例子中,它总是具有相同的顺序,因为您的两个关键元素
var key=new Func(()=>true)
都生成相同的哈希代码。您可以使用
GetHashCode()
检查它。如果两个键具有相同的哈希代码,它们将被添加到同一个bucket中。每个bucket只是一个列表,其中包含添加它们的项的顺序。

因为在循环中它将打印字典的第一个值。相反,如果你使用字典或foreach,那么你可以全部打印出来。老实说,这是一个非常奇怪的问题。for 0到40循环的作用是什么?我看不出有什么用。还有,为什么要使用Func作为键?从未见过。我使用Func是因为我不能有两个值为true的键。在循环中,我得到第一个值,它的键返回true。我只是想了解这一点behavior@Chidambaram来自msdn站点:为了枚举的目的,字典中的每个项都被视为表示值及其键的KeyValuePair结构。项目返回的顺序尚未定义。没有人说过字典的行为与有序集合不同。只是不能保证。在当前实现中,在不删除项之前,顺序是稳定的。从msdn:为了枚举的目的,字典中的每个项都被视为表示值及其键的KeyValuePair结构。返回项目的顺序未定义。因此,如果顺序未定义,为什么我总是只获取第一个元素?@BudaGavril,因为这是一个实现细节。新版本的.Net可能会改变这一点。@MatthewWatson我明白了。Thanks@BudaGavril请参阅:它显示元素的枚举顺序似乎与它们在字典中插入的顺序相同,但正如Matthew Watson所说,顺序是一个需要更改的实现细节,因此永远不要指望它会告诉您详细的答案。”(对于字典)…顺序取决于键生成的哈希值”:那不是真的。字典中元素的顺序是未来版本中可能更改的实现细节,而现在似乎是插入顺序。您必须阅读整个句子“因此顺序取决于键对象生成的哈希值和存储桶的数量。”。bucket是由GetHashCode%NumberOfBucket选择的。在我的示例中,键是随机整数(GetHasCode本身返回整数),看起来顺序取决于顺序插入,而不是键的哈希代码。我说的是字典的枚举顺序,这似乎是字典中“顺序”唯一有意义的含义@StefanKirsch,我错过了什么吗?是的,这是真的。现在我明白了。我已经检查了实现,并且有一个列表,其中将根据添加顺序添加项目。但是,如果您删除一些项目,然后再次添加它们,它将不会具有该顺序。新项目将获得已删除项目的位置。因此,如果删除第一项并添加新项。最后添加的项目将是第一个。