本文介绍了是静态类初始化在C#中的顺序确定的?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经做了一些搜索,我认为下面code为保证产生的输出:

I've done some searching and I think the following code is guaranteed to produce output:

B.X = 7

B.X = 0

A.X = 1

A = 1,B = 0

A = 1, B = 0

static class B
{
    public static int X = 7;
    static B() {
        Console.WriteLine("B.X = " + X);
        X = A.X;
        Console.WriteLine("B.X = " + X);
    }
}

static class A
{
    public static int X = B.X + 1;
    static A() {
        Console.WriteLine("A.X = " + X);
    }
}

static class Program
{
    static void Main() {
        Console.WriteLine("A = {0}, B = {1}", A.X, B.X);
    }
}

我已经运行这个无数次,始终得到code部分上面的输出;我只是想验证它永远不会改变?即使文字上,A类和B类被重新安排?

I've run this numerous times and always get the output above the code section; I just wanted to verify it will never change? Even if textually, class A and class B are re-arranged?

它是保证第一次使用一个静态对象将触发它的静态成员的初始化,然后通过实例的静态构造函数?对于这个方案,主要采用A.X将触发A.X,进而初始化B.X,那么B()和精加工A.X的初始化后的初始化,将进入A()。最后的Main()将输出A.X和B.X。

Is it guaranteed that the first use of a static object will trigger the initialization of its static members, followed by instantiating its static constructor? For this program, using A.X in main will trigger the initialization of A.X, which in turn initializes B.X, then B() and after finishing the initialization of A.X, will proceed to A(). Finally Main() will output A.X and B.X.

推荐答案

直接从ECMA-334:

Straight from ECMA-334:

17.4.5.1:如果一个静态构造函数(§17.11)中的类存在,静态字段初始执行发生之前立即执行该静态构造函数的否则,静态字段初始是在之前的第一次使用这个类的静态字段的实现相关的时间执行。

17.11:静态构造函数的执行是由第一触发
  下列事件的一个应用领域内发生:


      
  • 类的一个实例被创建。

  •   
  • 任何类的静态成员的参考。

  •   

如果一个类包含在其中开始执行,静态构造函数该类的主要方法(§10.1)
  执行称为主方法之前。的如果一个类包含任何初始化静态字段,这些
  初始化在文本顺序执行静态构造函数(§17.4.5)之前立即执行。

If a class contains the Main method (§10.1) in which execution begins, the static constructor for that class executes before the Main method is called. If a class contains any static fields with initializers, those initializers are executed in textual order immediately prior to executing the static constructor (§17.4.5).

所以顺序是:


  • A.X 使用,所以静态A()调用。

  • AX 需要初始化,但它使用 BX ,所以静态B( )调用。

  • B.X 需要初始化,并且它被初始化为7 B.X = 7

  • B 所有的静态字段都被初始化,所以称为静态B() X 打印(7),然后将其设置为 A.X A 已经开始被初始化,所以我们得到 AX ,这是默认值(的值时,类初始化,在类的所有静态字段首先被初始化为它们的默认值); B.X = 0 ,并打印(0)。

  • 完成初始化 B AX的值设置为 B.X +1 A.X = 1

  • A 的所有静态字段被初始化,所以静态A()被调用。 A.X 打印(1)。

  • 早在 AX的值 BX 打印(1,0)。

  • A.X used, so static A() called.
  • A.X needs to be initialized, but it uses B.X, so static B() called.
  • B.X needs to be initialized, and it is initialized to 7. B.X = 7
  • All static fields of B are initialized, so static B() is called. X is printed ("7"), then it is set to A.X. A has already started being initialized, so we get the value of A.X, which is the default value ("when a class is initialized, all static fields in that class are first initialized to their default value"); B.X = 0, and is printed ("0").
  • Done initializing B, and the value of A.X is set to B.X+1. A.X = 1.
  • All static fields of A are initialized, so static A() is called. A.X is printed ("1").
  • Back in Main, the values of A.X and B.X are printed ("1", "0").

实际上在此标准中评论:

It actually comments upon this in the standard:

17.4.5: 为在其默认值状态观察变量初始化静态字段这是可能的。然而,这是强烈反对的风格问题。

这篇关于是静态类初始化在C#中的顺序确定的?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

11-02 20:23