为什么在使用初始化器,构造函数和方法调用时,print语句按此顺序执行?

时间:2014-10-22 10:26:08

标签: java

这是我正在运行的代码,此代码的输出是4 2 1 3,有人可以解释为什么结果按此顺序打印。

public class goFuncTest {
        goFuncTest() 
        {
             System.out.print("1 ");                
        } 
        {               
             System.out.print("2 ");            
        } 
        public static void main(String[] args)
        { 

            new goFuncTest().go(); 
        } 
        void go()
        { 
             System.out.print("3 ");                
        } 
        static
        { 
            System.out.print("4 ");                 
        } 

    } 

4 个答案:

答案 0 :(得分:4)

根据您最近的问题编辑,您的输出将是4 2 1 3.首先运行静态初始化程序,然后运行实例初始化程序。如果你有多个相同类型的初始值设定项,它们将按照它们在类中出现的顺序执行。

// static initializer first
static {
  System.out.print("4 ");
}

// then instance initializer
{ 
  System.out.print("2 "); 
} 

接下来构造函数会启动,它会给你:

goFuncTest() 
{
  System.out.print("1 "); 
} 

最后调用该方法:

void go()
{ 
  System.out.print("3 "); 
} 

答案 1 :(得分:1)

正如JB Nizet在第一次评论中指出的那样,结果应该是2,4,3,1。

接下来,首先执行静态块,然后执行初始化块。在您的代码中,没有静态块,只有 inti 块。

初始化块执行的顺序是它们在源代码-2,4中的顺序。

根据构造函数和方法调用剩下两个结果。 1,3

现在你可以看到答案了吗?

答案 2 :(得分:0)

原因:

  1. 你有一个实例块,它按顺序执行,出现在你的类定义中。因此2首先出现,然后出现4,因此输出2 4
  2. 接下来你要调用新的goFuncTest(),它将调用你的构造函数,因此你会在输出中看到1。
  3. 现在你的实例上你正在调用go方法打印3。

答案 3 :(得分:0)

似乎主要的混乱只是因为不理解一个班级可以拥有的各种块;

this answer给出了一个很好的例子和解释;

以下是他们提供的代码:

public class Test {

    static int staticVariable;
    int nonStaticVariable;        

    // Static initialization block:
    // Runs once (when the class is initialized).
    static {
        System.out.println("Static initalization.");
        staticVariable = 5;
    }

    // Instance initialization block:
    // Runs before the constructor each time you instantiate an object
    {
        System.out.println("Instance initialization.");
        nonStaticVariable = 7;
    }

    public Test() {
        System.out.println("Constructor.");
    }

    public static void main(String[] args) {
        new Test();
        new Test();
    }
}

此课程有static initialiserinstance initialisation blockconstructorclass method

static initialiserstatic {...} instance initialiser{...} constructorPublic ClassName(){...} class methodPublic Static Whatever classMethod(String[] args){...}

在不同情况下调用这些中的每一个;在加载类时调用static initialiser,没有其他方法可以调用它,你甚至无法通过反射来实现它,因为它永远不会被method instance表示,它由JVM调用

每当你在构造函数之前创建类的实例 - 时,都会调用instance initialiser

您可以拥有多个static initialiser和多个instance initialiser,并按照它们在代码中显示的顺序执行。

您可能已经知道

constructorclass method

在您的示例中,稍微重新排列代码可能会更有帮助,以更好地反映该层次结构;

public class goFuncTest {

    //static instance initialiser
    static { 
        System.out.print("4 ");                 
    } 

    //instance initialiser
    {               
        System.out.print("2 ");            
    } 

    //Constructor
    goFuncTest(){
        System.out.print("1 ");                
    }

    //Class method
    void go(){ 
        System.out.print("3 ");                
    } 


    public static void main(String[] args){ 
        new goFuncTest().go(); 
    } 

} 

(编辑为添加静态关键字)