【发布时间】:2014-07-16 13:45:17
【问题描述】:
我有一个 CustomObject 数组和一个自定义 IEqualityComparer<CustomObject>。我已经硬编码了IEqualityComparer.GetHashCode() 方法来返回一个常量42。
当我在数组上运行 linq 的 Distinct 方法时,没有过滤掉任何内容。有人知道为什么吗?
注意:我知道这里有很多关于这个问题的问题,但是,我见过的那些(C# Distinct on IEnumerable<T> with custom IEqualityComparer、Distinct() with lambda? 等)只是说要确保实施GetHashCode。他们都没有解释,为什么它不起作用。
代码:
public class CustomObject
{
public string Name { get; set; }
}
public class CustomObjectEqualityComparer : IEqualityComparer<CustomObject>
{
public bool Equals(CustomObject x, CustomObject y)
{
//Every CustomObject should now be 'equal'!
return x.GetHashCode() == y.GetHashCode();
}
public int GetHashCode(CustomObject obj)
{
//Every CustomObject should now be 'equal'!
return 42;
}
}
测试:
[TestFixture]
public class TestRunner
{
private CustomObject[] customObjects =
{
new CustomObject {Name = "Please"},
new CustomObject {Name = "Help"},
new CustomObject {Name = "Me"},
new CustomObject {Name = "Stack"},
new CustomObject {Name = "Overflow"},
};
[Test]
public void DistinctTest()
{
var distinctArray =
customObjects.Distinct(new CustomObjectEqualityComparer()).ToArray();
//Since every CustomObject is 'Equal' there should only be
//1 element in the array.
Assert.AreEqual(1, distinctArray.Length);
}
}
这是我运行测试得到的输出:
Expected: 5
But was: 1
如果我调试测试,我可以看到 GetHashCode 正在被调用,那么为什么 Distinct 没有过滤掉所有的“重复项”?
【问题讨论】:
-
如果相关,我使用
.net 4.5.1 -
简单,您在相等期间在
CustomObject上调用GetHashCode,而不是调用您的硬编码版本。Distinct实现是使用自定义比较器的。它将首先调用GetHashCode。如果发生冲突,它将调用Equals,您在CustomObject上没有覆盖它,因此将是一个参考哈希码。 -
但是我传递了我的
CustomObjectEqualityComparer。比较应该委托给这个类,对吧? -
该死,在阅读 Jon Skeet 的回复后,我现在明白了,你是对的 @AdamHouldsworth。谢谢!
标签: c# .net linq linq-to-objects