【问题标题】:How to check equality of boxed object of value types when types are different but compatible to compare the values当类型不同但兼容比较值时如何检查值类型的装箱对象的相等性
【发布时间】:2018-01-15 11:52:54
【问题描述】:

当我们装箱两个值类型(它们是不同类型但兼容以比较值,例如:int 和 short)并尝试调用 Equals 方法时,即使值相同,也会给出 false。

案例 1:

int a = 5;
short b = 5;
var ob_a = (object) a;
var ob_b = (object) b;
var result = a == b; // true
var result_for_objects = ob_a.Equals(ob_b); // false

另一方面,当两个值类型相同时,Equals 返回实际值比较结果。

案例 2:

int a = 5;
int b = 5;
var ob_a = (object) a;
var ob_b = (object) b;
var result = a == b; // true
var result_for_objects = ob_a.Equals(ob_b); // true

我比较了这两种情况的反汇编代码,但它是相同的,我无法找到任何区别。

            var result = a == b;
012404DE  mov         eax,dword ptr [ebp-40h]  
012404E1  cmp         eax,dword ptr [ebp-44h]  
012404E4  sete        al  
012404E7  movzx       eax,al  
012404EA  mov         dword ptr [ebp-50h],eax  
            var result_for_objects = ob_a.Equals(ob_b);
012404ED  mov         ecx,dword ptr [ebp-48h]  
012404F0  mov         edx,dword ptr [ebp-4Ch]  
012404F3  mov         eax,dword ptr [ecx]  
012404F5  mov         eax,dword ptr [eax+28h]  
012404F8  call        dword ptr [eax+4]  
012404FB  mov         dword ptr [ebp-5Ch],eax  
012404FE  movzx       eax,byte ptr [ebp-5Ch]  
01240502  mov         dword ptr [ebp-54h],eax  
  1. 如果装箱对象中的值类型不同,实际调用的是哪个 Equals 方法?
  2. 当装箱对象内的两种值类型相同时,它如何调用该值类型的 Equals 方法?

【问题讨论】:

    标签: c# .net referenceequals


    【解决方案1】:

    变量的类型保存在对象中。

    例如:

    Console.Write(ob_a.GetType().ToString());   // will give you System.Int32
    Console.Write(ob_b.GetType().ToString());   // will give you System.Int16
    

    它还通过方法提供不同的哈希码:GetHashCode()

    如果您将短变量转换为 int 或其他方式,它将是相等的......所以基本上问题在于不同的变量类型。

    以下是这两个问题的答案:http://www.ikriv.com/dev/dotnet/ObjectEquality.html

    由于对 Equals() 的调用是虚拟的,x.Equals(y) 将调用的方法的确切版本由 x 的动态类型决定,这通常在编译时是未知的。另请注意,与 a==b 不同,表达式 x.Equals(y) 本质上是不对称的。只有 x 指示将调用哪个版本的 Equals()。 y 在这件事上绝对没有发言权。

    【讨论】:

    • 谢谢! “如果操作数属于不同类型,Equals() 总是返回 false。如果操作数属于同一类型,则按值进行比较”不知道。
    猜你喜欢
    • 1970-01-01
    • 2020-08-07
    • 2019-08-18
    • 2019-05-29
    • 1970-01-01
    • 1970-01-01
    • 2012-10-10
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多