为类生成哈希码时,是否可以使用该类成员的哈希码?这是一个示例类:
class Sample
{
private readonly string _strA, _strB;
public Sample(string strA, string strB)
{
this._strA = strA;
this._strB = strB;
}
public override int GetHashCode()
{
return (this._strA + "###" + this._strB).GetHashCode();
}
}
我认为只要_strA和_strB都不包含字符串“###”,这都会有效。我不完全确定,因为我不知道如何在字符串上生成哈希码的具体细节。
我在Create a hashcode of two numbers的帖子中看到了一个解决方案,我可以为我的目的定制,但我认为我的解决方案更简单(只要两个字符串都不包含“###”)。
答案 0 :(得分:2)
如果你有几个字段对一个对象的整体哈希码有贡献,那么一个简单而有效的方法就是:
public override int GetHashCode()
{
int hash = 17;
hash = hash*23 + field1.GetHashCode();
hash = hash*23 + field2.GetHashCode();
hash = hash*23 + field3.GetHashCode();
// And so on for all applicable fields.
// field1, field2 and field3 are all class field members.
return hash;
}
答案 1 :(得分:1)
更好的方法是以数学方式组合哈希码,using something like the Times 33 hash。在当前代码中,每次调用GetHashCode
时都会创建一个临时字符串,这可能会导致性能不佳。
public override int GetHashCode()
{
// omit null-coalesce if we know them to be non-null
return (33 * (this._strA ?? "").GetHashCode())
+ (this._strB ?? "").GetHashCode();
}
如果你的类真的是不可变的,预先计算哈希码可能值4字节:
private readonly int _hash;
public Sample(string strA, string strB)
{
this._strA = strA;
this._strB = strB;
this._hash = (33 * (this._strA ?? "").GetHashCode())
+ (this._strB ?? "").GetHashCode();
}
public override int GetHashCode()
{
return this._hash;
}