0

首先,我已经阅读了这个答案,不,它只说明了它现在是如何实现的,但没有解释为什么。

这是一个示例程序(与此处相同):

class Program
{
    static void Main()
    {
        try {
            implMain();
        } catch (Exception e) {
            Console.WriteLine(e.ToString());
        }
    }

    static void implMain()
    {
        for (int i = 0; i < 10; i++) {
            invoke(() => {
                Console.WriteLine(i);
                throw new InvalidOperationException();
            });
        }
    }
    static void invoke(Action what)
    {
        what();
    }
}

它输出以下调用堆栈:

System.InvalidOperationException
at ConsoleApplication1.Program.<>c__DisplayClass2.<implMain>b__0()
at ConsoleApplication1.Program.invoke(Action what)
at ConsoleApplication1.Program.implMain()
at ConsoleApplication1.Program.Main()

注意这两行:

at ConsoleApplication1.Program.<>c__DisplayClass2.<implMain>b__0()
at ConsoleApplication1.Program.invoke(Action what)

较低的 (with invoke()) 表示其中有ConsoleApplication1带有类的名称空间Program,其中有 member invoke()。这里从左到右对应于从外到内。

上面的(带c__DisplayClass2)再次表示有一个命名空间和一个类......

然后c__DisplayClass2是“编译器选择用于存储捕获的变量的神奇名称”,然后就<implMain>好像它是c__DisplayClass2. 所以它读起来好像不知何故c__DisplayClass2是.ProgramimplMainc__DisplayClass2

现在我看到它在逻辑上是相反的——有方法,有专门为局部变量设计implMain()的“魔术类” 。所以对我来说,上面的行看起来应该是这样的:c__DisplayClass2implMain()

at ConsoleApplication1.Program.implMain.c__DisplayClass2.b__0()

(也许有一些额外的符号来防止可能的冲突)但我希望我的想法很清楚——这样它看起来就像c__DisplayClass2是专门为促进implMain()功能而设计的。

implMain当前实现在局部变量捕获类名()之后显示方法名( c__DisplayClass2)而不是反之亦然,是否有任何理由?

4

1 回答 1

3

<implMain>b__0()只是方法的名称。

反汇编程序中的检查会告诉您这一点。<and>并不意味着泛型。

包含implMain可能只是提示创建委托的位置。

于 2013-05-08T10:16:07.267 回答