【发布时间】:2011-05-21 05:30:55
【问题描述】:
在内部,哈希如何查找键来获取值?
会是 bin 排序吗?
【问题讨论】:
-
@Gabe:我猜他的意思是:“二进制排序”
-
我想如果他问的是字典,二分搜索是有道理的,但散列有点暗示散列。
标签: c# dictionary hash
在内部,哈希如何查找键来获取值?
会是 bin 排序吗?
【问题讨论】:
标签: c# dictionary hash
字典使用哈希码来计算存储条目的桶的编号。桶的数量被选择为素数,并且特定密钥的桶数被计算为密钥的哈希码以桶的数量为模。因为多个对象可以具有相同的哈希码,并且多个哈希码可以落在同一个桶中,所以当在桶中找到一个键时,还必须比较它是否相等,以确保它是正确的键。如果在bucket中发现了不正确的key,则使用错误条目的next成员来查找下一个位置来搜索所需的key。
该算法的结果是,当没有冲突时,可以非常快速地找到正确的存储桶 - O(1),但在最坏的情况下,字典中存储的条目数量可能需要线性时间。我在这里假设一个对象的哈希码可以在恒定时间内计算出来。
.NET实现中的实际代码可以通过下载参考实现源码查看,也可以使用.NET Reflector查看:
private int FindEntry(TKey key)
{
if (key == null)
{
ThrowHelper.ThrowArgumentNullException(ExceptionArgument.key);
}
if (this.buckets != null)
{
int num = this.comparer.GetHashCode(key) & 0x7fffffff;
for (int i = this.buckets[num % this.buckets.Length]; i >= 0; i = this.entries[i].next)
{
if ((this.entries[i].hashCode == num) && this.comparer.Equals(this.entries[i].key, key))
{
return i;
}
}
}
return -1;
}
【讨论】:
哈希只是针对一个键运行的算法,它创建(希望)一个唯一值,该值指向存储项目的存储桶。因此,当您计算值以尝试检索该项目时,您希望是哈希将指向您之前保存的对象。如果没有,应该有一个指针,指示在哪里寻找下一个共享这个散列值的对象。当您找到您的物品时,它会返回。如果到达链的末端,则无法找到您的项目。
请参阅 Hash Tables 和 Hash Function 了解更完整的哈希定义。
【讨论】: