ハーブスタッターのRedditに関する投稿を読みました:JITはネイティブほど速くなることはなく、誰かがハーブと呼ばれる誰かが非仮想ではなく仮想メソッドを使用していることを「誤解」しているとコメントしました(記事はこちらで読むことができます) )。それは私に考えさせられました、そして私は簡単な小さなプログラムを作りました、そしてC#が実際にCILのための仮想メソッド(callvirt対call)を生成することに気づきました。しかし、それはそれほど簡単ではなく、JITはvtablesと動的ディスパッチを使用する代わりにコードをインライン化する可能性があると言われました。デバッガーを起動して、確認しようとしました。これが私の簡単なプログラムです:
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
Test t = new Test();
t.TestIt();
t.TestOut();
}
}
class Test
{
public Test() { }
public void TestIt()
{
Console.WriteLine("TESTIT");
}
public void TestOut()
{
Console.WriteLine("TESTOUT");
}
}
}
そして、ここにアセンブリがあります:
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
Test t = new Test();
00000000 push ebp
00000001 mov ebp,esp
00000003 push esi
00000004 mov ecx,439E68h
00000009 call FFCE0AD4
0000000e mov esi,eax
t.TestIt();
00000010 call 704BBEB8 // Call to Console.WriteLine()
00000015 mov ecx,eax
00000017 mov edx,dword ptr ds:[02A02088h]
0000001d mov eax,dword ptr [ecx]
0000001f call dword ptr [eax+000000D8h]
t.TestOut();
00000025 call 704BBEB8 // Call to Console.WriteLine()
0000002a mov ecx,eax
0000002c mov edx,dword ptr ds:[02A0208Ch]
00000032 mov eax,dword ptr [ecx]
00000034 call dword ptr [eax+000000D8h]
0000003a pop esi
}
0000003b pop ebp
0000003c ret
私の質問はこれです:アセンブリを見ると、動的ディスパッチを使用しているかどうかをどのように判断できますか?私の勘は、プログラミング言語のクラスで覚えているものに似ているこれらの4つの命令によるものです。
0000002a mov ecx,eax
0000002c mov edx,dword ptr ds:[02A0208Ch]
00000032 mov eax,dword ptr [ecx]
00000034 call dword ptr [eax+000000D8h]
これが動的ディスパッチであると仮定して正しいですか?もしそうなら、他に物語の兆候はありますか?私が間違っている場合、それが動的ディスパッチであるかどうかをどのように判断できますか?