13

看完这个问题为什么“int”和“sbyte”GetHashCode函数会产生不同的值?我想进一步挖掘并发现以下行为:

sbyte i = 1;            
int j = 1;
object.Equals(i, j) //false (1)
object.Equals(j, i) //false (2) 
i.Equals(j) //false (3)
j.Equals(i) //true (4)
i == j //true (5)
j == i //true (6)
i.GetHashCode() == j.GetHashCode() //false (7)
  1. (3) 和 (4) 之间的差异打破了 Equals 应该是对称的要求。
  2. (2) 和 (4) 之间的区别与MSDN 规范不一致:

    如果这两个对象不代表同一个对象引用且都不为 null,则调用 objA.Equals(objB) 并返回结果。这意味着如果 objA 覆盖 Object.Equals(Object) 方法,则调用此覆盖。

  3. (3) 和 (5) 之间的差异意味着 operator == 返回 true,但是对象在 Equals 方面并不相等。
  4. (4), (5), (6) 和 (7) 之间的区别意味着两个对象在运算符 == 和 Equals 方面是相等的,但是它们具有不同的哈希码。

如果有人能解释为什么我认为在相当基本的 .NET 类型中观察到这种不一致的行为,我将非常感兴趣。

4

1 回答 1

15

您的问题是您错过了i.Equals(j). 它去过载int.Equals(int)。在这里,您正在比较i(int)j,它们是相同的。相同的隐式转换发生在==.

其他比较适用于 anint和 a sbyte,根据定义,它们是不同的。j.Equals(i)转到重载int.Equals(object),因为参数不能隐式转换为sbyte.

Equals对他们来说是对称的,但你的调用代码不是。如果你用 抑制隐式转换i.Equals((object)j),它会返回false,表明它Equals确实是对称的。

于 2012-09-19T20:45:57.180 回答