64位gethashcode是否可用于对象?

时间:2013-09-09 10:56:38

标签: c# 64-bit hashcode

我正在使用字典,我想覆盖密钥的GetHashCode功能。但我需要一个64位哈希码。

有没有解决方案?

2 个答案:

答案 0 :(得分:4)

不,你不能。 GetHashCode的签名固定为virtual int GetHashCode()

请注意,Dictionary<TKey, TValue> 执行处理具有相同哈希码的多个项目。您可以通过重载这样的GetHashCode来尝试它:

public override GetHashCode()
{
    return 0;
}

这会使字典变得非常慢(它会在其中搜索O(n)而不是O(1))!

Dictionary<,>通过使用Equals方法查看每个对象来处理具有相同键的多个对象(因此这是一个两步过程,首先是GetHashCode,然后是{{1}在具有相同Equals)的所有项目之间。

要将64位GetHashCode更改为32位GetHashCode,您可以简单地:

GetHashCode

:-)

或者,如果你更喜欢漫长的道路:

long hash64 = ....;
int hash32 = hash64.GetHashCode();
return hash32;

如果您有兴趣,here会解释long hash64 = ....; unchecked { int hash32 = ((int)hash64) ^ ((int)(hash64 >> 32)); return hash32; } 内部如何运作。查看Dictionary<,>

我对Zobrist哈希进行了一些研究......看起来你应该忽略64位冲突的可能性。如果你想模拟这个,你可以做类似的事情:

The System.Collections.Generic.Dictionary Class

在这个例子中,你不比较public class HashPiece { public readonly long Hash64; public readonly Piece[] Board = new Piece[64]; public int GetHashCode() { return Hash64.GetHashCode(); } public bool Equals(object other) { return this.Hash64 == ((HashPiece)other).Hash64; } } 数组,你只希望完整的64位哈希是正确的。显然,另一个解决方案是:

Piece[]

请注意,我发现anecdotical experience随机数生成器的质量以及所使用的种子值的单个值会影响碰撞次数。

答案 1 :(得分:1)

我使用下面的代码生成64位HashCode,主要是作为长重复字符串的替代。

 public long ComputeHash(String p_sInput)
 {
        MD5CryptoServiceProvider md5 = new MD5CryptoServiceProvider();
        byte[] hash = md5.ComputeHash(Encoding.ASCII.GetBytes(p_sInput));
        return BitConverter.ToInt64(hash, 0);
 }