:Int32.ToString()がcallvirtではなくcall命令を発行するのはなぜですか?次のコードについて
struct Test
{
public override string ToString()
{
return "";
}
}
public class Program
{
public static void Main()
{
Test a = new Test();
a.ToString();
Int32 b = 5;
b.ToString();
}
}
コンパイラは、次のIL発する:値型Test
両方ので
.locals init ([0] valuetype ConsoleApplication2.Test a,
[1] int32 b)
IL_0000: nop
IL_0001: ldloca.s a
IL_0003: initobj ConsoleApplication2.Test
IL_0009: ldloca.s a
IL_000b: constrained. ConsoleApplication2.Test
IL_0011: callvirt instance string [mscorlib]System.Object::ToString()
IL_0016: pop
IL_0017: ldc.i4.5
IL_0018: stloc.1
IL_0019: ldloca.s b
IL_001b: call instance string [mscorlib]System.Int32::ToString()
IL_0020: pop
IL_0021: ret
およびInt32
ToString()
メソッドをオーバーライドし、私はボクシングの両方a.ToString()
に生じないと思いますb.ToString()
。だから、私はなぜコンパイラが + callvirt
をTest
に、call
をInt32
のために出すのだろうか?
ありがとう、私はそれがコンパイラの最適化作業であると推測します。しかし私は私の推測を支える資料を見つけることはできません。ですから、プリミティブ型のこの特別な最適化に関するドキュメントを提供できれば幸いです。再度、感謝します。 –
@LifuHuang私の答えを更新しました。 –
@Eli Arbelありがとう、あなたは本当に私の質問を解決しました:) –