gpt4 book ai didi

C# - 值类型等于方法 - 为什么编译器使用反射?

转载 作者:可可西里 更新时间:2023-11-01 03:08:08 26 4
gpt4 key购买 nike

我刚刚遇到了一些对我来说很奇怪的事情:当你在一个值类型上使用 Equals() 方法时(当然,如果这个方法没有被覆盖)你会得到一些非常非常慢 - 使用反射对字段进行一对一比较!如:

public struct MyStruct{
int i;
}

(...)

MyStruct s, t;
s.i = 0;
t.i = 1;
if ( s.Equals( t )) /* s.i will be compared to t.i via reflection here. */
(...)

我的问题:为什么 C# 编译器不生成比较值类型的简单方法?类似于(在 MyStruct 的定义中):

   public override bool Equals( Object o ){
if ( this.i == o.i )
return true;
else
return false;
}

编译器在编译时就知道MyStruct的字段是什么,为什么要等到运行时才枚举MyStruct的字段?

对我来说很奇怪。

谢谢:)

ADDED :抱歉,我只是意识到,当然,Equals 不是语言关键字而是运行时方法...编译器完全不知道此方法.所以在这里使用反射是有意义的。

最佳答案

以下是从mscorlib中反编译出的ValueType.Equals方法:

public override bool Equals(object obj)
{
if (obj == null)
{
return false;
}
RuntimeType type = (RuntimeType) base.GetType();
RuntimeType type2 = (RuntimeType) obj.GetType();
if (type2 != type)
{
return false;
}
object a = this;
if (CanCompareBits(this))
{
return FastEqualsCheck(a, obj);
}
FieldInfo[] fields = type.GetFields(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);
for (int i = 0; i < fields.Length; i++)
{
object obj3 = ((RtFieldInfo) fields[i]).InternalGetValue(a, false);
object obj4 = ((RtFieldInfo) fields[i]).InternalGetValue(obj, false);
if (obj3 == null)
{
if (obj4 != null)
{
return false;
}
}
else if (!obj3.Equals(obj4))
{
return false;
}
}
return true;
}

如果可能,将进行逐位比较(注意 CanCompareBits 和 FastEqualsCheck,它们都被定义为 InternalCall。JIT 可能会在此处注入(inject)适当的代码。至于为什么这么慢,我不能'不告诉你。

关于C# - 值类型等于方法 - 为什么编译器使用反射?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1009394/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com