无参数构造函数中的第一个参数是什么?

LmT*_*oon 14 c# constructor cil

我有这样简单的程序:

public class Foo
{
    public Foo()
    {
    }
    public int MyInt { get; set; } = 10;
    public List<int> MyList { get; set; } = new List<int>();
}

public class Program
{
    static public void Main()
    {
        Console.WriteLine(new Foo().MyInt);
        Console.ReadLine();
    }
}
Run Code Online (Sandbox Code Playgroud)

我决定看看这样的程序的CIL代码(我对Foo的构造函数感兴趣).就这个:

.method public hidebysig specialname rtspecialname
        instance void  .ctor() cil managed
{
    // Code size       26 (0x1a)
    .maxstack  8
    IL_0000:  ldarg.0
    IL_0001:  ldc.i4.s   10
    IL_0003:  stfld      int32 Foo::'<MyInt>k__BackingField'
    IL_0008:  ldarg.0
    IL_0009:  newobj     instance void class [mscorlib]System.Collections.Generic.List`1<int32>::.ctor()
    IL_000e:  stfld      class [mscorlib]System.Collections.Generic.List`1<int32> Foo::'<MyList>k__BackingField'
    IL_0013:  ldarg.0
    IL_0014:  call       instance void [mscorlib]System.Object::.ctor()
    IL_0019:  ret
} // end of method Foo::.ctor
Run Code Online (Sandbox Code Playgroud)

我想知道,当我看到第二行时,ldarg.0它是什么意思?this指针?但该对象尚未创建.我该如何修改其成员?我的假设是在调用构造函数之前,clr首先为对象分配内存.然后将成员初始化为默认值,然后调用构造函数.对象调用的最后一个有趣的时刻.我认为这将是第一次.

Dam*_*ver 10

字段初始值设定项是C#功能,而不是CLR功能.当你编写一个字段初始化程序时,C#编译器必须将代码放在某个地方,并将它放在任何构造函数体内.

由于这些初始化程序在构造函数"之前"运行,这就是为什么稍后运行实际的基类构造函数.

(所以,是的,第一个参数是你推断的那样this)