Я могу упростить ваш вопрос до:
public class C
{
public void M()
{
int x = 3;
Action action = () => Console.WriteLine(x);
// 'action' now points to method called something like "<M>b__0"
}
}
Если мы поместим этот код в замечательный sharplab , мы увидим, что сгенерировал компилятор:
public class C
{
[CompilerGenerated]
private sealed class <>c__DisplayClass0_0
{
public int x;
internal void <M>b__0()
{
Console.WriteLine(x);
}
}
public void M()
{
<>c__DisplayClass0_0 <>c__DisplayClass0_ = new <>c__DisplayClass0_0();
<>c__DisplayClass0_.x = 3;
Action action = <>c__DisplayClass0_.<M>b__0;
}
}
Поскольку action
захватывает переменную x
, компилятору пришлось создать целый новый класс с именем <>c__DisplayClass0_0
, в котором есть поле x
.Этот класс имеет метод с именем <M>b__0()
, который использует значение поля x
при вызове Console.WriteLine
.
В методе M()
вместо <>c__DisplayClass0_0.x
используется поле *1019*локальная переменная x
.
Делегат action
указывает на метод <M>b__0()
в этом экземпляре <>c__DisplayClass0_0
.