我有两个列表,我想比较.所以我创建了一个实现IEqualityComparer
接口的类,请参见下面的代码底部.
当我单步GetHashCode
执行代码时,代码会通过我的实现而不是Equals
?GetHashCode
尽管在互联网上阅读以及它到底在做什么,但我并不真正理解这种方法.
List<FactorPayoffs> missingfactorPayoffList =
factorPayoffList.Except(
factorPayoffListOrg,
new FactorPayoffs.Comparer()).ToList();
List<FactorPayoffs> missingfactorPayoffListOrg =
factorPayoffListOrg.Except(
factorPayoffList,
new FactorPayoffs.Comparer()).ToList();
Run Code Online (Sandbox Code Playgroud)
所以在上面的两行代码中,两个列表返回每个项目,告诉我这两个列表不包含任何相同的项目.事实并非如此,只有不同的行.我猜这种情况正在发生,因为该Equals
方法没有被调用,这反过来让我想知道我的GetHashCode
方法是否正常运作?
class FactorPayoffs
{
public string FactorGroup { get; set; }
public string Factor { get; set; }
public DateTime dtPrice { get; set; }
public DateTime dtPrice_e { get; set; }
public double Ret_USD { get; set; }
public class Comparer : IEqualityComparer<FactorPayoffs>
{
public bool Equals(FactorPayoffs x, FactorPayoffs y)
{
return x.dtPrice == y.dtPrice &&
x.dtPrice_e == y.dtPrice_e &&
x.Factor == y.Factor &&
x.FactorGroup == y.FactorGroup;
}
public int GetHashCode(FactorPayoffs obj)
{
int hash = 17;
hash = hash * 23 + (obj.dtPrice).GetHashCode();
hash = hash * 23 + (obj.dtPrice_e).GetHashCode();
hash = hash * 23 + (obj.Factor ?? "").GetHashCode();
hash = hash * 23 + (obj.FactorGroup ?? "").GetHashCode();
hash = hash * 23 + (obj.Ret_USD).GetHashCode();
return hash;
}
}
}
Run Code Online (Sandbox Code Playgroud)
Jon*_*Jon 25
您Equals
和GetHashCode
实现应该涉及完全相同的属性集; 他们不.
在更正式的术语中,GetHashCode
必须始终为两个比较相等的对象返回相同的值.使用当前代码,两个仅在Ret_USD
值上不同的对象将始终比较相等,但不保证具有相同的哈希码.
所以会发生什么是LINQ调用GetHashCode
你认为相等的两个对象,得到不同的值,得出的结论是,由于值不同,对象不能相等,所以在调用Equals
和移动时根本就没有意义.
要解决这个问题,要么Ret_USD
从GetHashCode
内部删除因子,要么在里面引入它Equals
(对于你的相等语义来说是有意义的).
Sam*_*ell 13
GetHashCode
旨在作为一个快速但粗略的相等估计,因此许多可能涉及大量比较的操作都是从检查此结果开始,而不是Equals
仅Equals
在必要时使用.特别是,如果x.GetHashCode()!=y.GetHashCode()
,那么我们已经知道x.Equals(y)
是假的,所以没有理由打电话Equals
.有x.GetHashCode()==y.GetHashCode()
,则x
可能等同y
,而只是调用Equals
会给出一个明确的答案.
如果你GetHashCode
以一种导致GetHashCode
两个Equals
返回对象不同的方式实现true
,那么你的代码中就会有一个错误,依赖这些方法的许多集合类和算法都会无声地失败.
如果要强制执行Equals,可以按如下方式实现
public int GetHashCode(FactorPayoffs obj) {
return 1;
}
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
6784 次 |
最近记录: |