具有泛型集合的 GetHashCode 返回不同的值

GetHashCode With Generic Collection Returns Different Values

提问人:user1617242 提问时间:11/15/2016 最后编辑:Communityuser1617242 更新时间:11/16/2016 访问量:295

问:

看起来哈希代码问题和实现你自己的平等逻辑已经被打死了,但我似乎找不到一个明确的答案。

我有一个自定义对象 (Step),它覆盖了 MSDN 文档建议的 Equals、GetHashCode、== 和 !=。这个对象本身工作正常;将 Step 与 Step 进行比较时,相等运算符按预期工作。请注意,我所说的相等是指 Step 属性的值,而不是引用相等。

我有第二个对象(Steps),它将Step对象存储在泛型列表中。现在,我想查看 Step 对象列表是否等于另一个 Step 对象列表。在 Steps 对象中,我重写了各种方法和运算符,就像我在 Step 中所做的那样。对于 GetHashCode 重写,我遍历了 Step 列表并组合了哈希代码:

foreach(var step in steplist.Steps)
{
    hash += step.GetHashCode()
}
return hash

简单。但它不起作用。具有相等 Step 对象值的两个单独列表的哈希代码返回不同的哈希代码。我假设我没有正确实现哈希代码覆盖。

我准备将返回的哈希代码硬编码为零并收工。任何见解都是值得赞赏的。

编辑:

对不起,我试图简短,以避免文字墙。下面是 Step 对象的哈希代码生成。摘自重写的 System.Object.GetHashCode 的最佳算法是什么?

public override int GetHashCode()
{
     return new { StepType, Color, Trigger, Delay, Index       }.GetHashCode();
}

请注意,除了 Delay 和 Index 之外,所有这些属性都是引用类型,而不是值类型(如果这有区别的话)。并回答某人的问题:不,我正在比较的两个列表绝对不是相同的参考。它们是两个单独的列表。也许这就是我的问题所在。

C# .NET 相等 性重写 GetHashCode

评论

3赞 Jon Skeet 11/15/2016
仅用那一小段代码很难分辨。请提供一个最小的可重复示例
1赞 Lasse V. Karlsen 11/15/2016
为了消除你的恐惧,它应该有效。因此,您的代码中一定存在错误。您显示的小代码可能表明,具有不同顺序的相同对象的两个列表将生成相同的哈希代码,但除此之外,我们无法告诉您为什么它在特定情况下有效或无效,因为没有足够的代码进行分析。请发布一个最小的可重现示例,以及您期望代码具有什么行为(它没有)。
0赞 Tamas Ionut 11/15/2016
你能发布 Step.GetHashCode() 实现吗?
0赞 Med.Amine.Touil 11/15/2016
您确定列表引用了相同的对象吗?

答:

0赞 Scott Chamberlain 11/16/2016 #1

您需要显示 for 的代码,并且还需要确定,但是如果它们不是相同的引用,并且您使用的是 for 这些类型的默认实现,则具有不同的引用会导致生成不同的哈希码。GetHashCode()StepTypeColorTriggerGetHashCode()