为什么在调用构造函数之前发生显式初始化

时间:2013-11-01 20:01:29

标签: java

我无法理解以下代码中的控制流程:

class Television {
    private int channel=setChannel(7);

    public Television (int channel) {
        this.channel=channel;
        System.out.println(channel + "");
    }

    public int setChannel(int channel) {
        this.channel=channel;
        System.out.print(channel + " ");
        return channel;
    }
}

public class TelevisionMain {
    public static void main(String[] args) {
        Television t = new Television(12);
    }
}

输出为7 12。

这意味着首先发生显式调用。 我是java新手,我认为执行从main开始,所以应该先调用构造函数。 任何人都可以解释为什么会这样。

4 个答案:

答案 0 :(得分:2)

初始化是构造的一部分,它定义为在调用super()之后和构造函数体之前发生。

  

应该首先调用构造函数。

是的。字段初始化是构造函数的一部分。

答案 1 :(得分:1)

您的Television构造函数大致编译为:

public Television(int channel)
{
    super();
    this.channel = this.setChannel(7);
    this.channel = channel;
    System.out.println(channel+"");
}

因此,当您致电Television t = new Television(12);时,它首先将频道设置为7,然后设置为12。

答案 2 :(得分:0)

最终答案是because the specification says it should。然而,这样做是合理的,因为反过来行为会使得无法覆盖默认的初始化值

如果订单首先是构造函数,那么其他所有订单都是

  • 叫做电视(12)
  • 在构造函数中将通道设置为12
  • 通道设置返回7 by int channel = setChannel(7);

这显然是一种不合理的事态,因为你永远不能使用默认值,因为构造函数无法更改这些默认值

答案 3 :(得分:0)

在Java中,基本上有一个隐藏的默认构造函数。如果不声明一个,则可以使用默认变量初始化类顶部的变量。无论如何,这就是我们想要的方式。实际情况是每个类都有一个静态块,其中变量可以在类加载过程中实际构造函数声明命中之前声明和播放。

我觉得你的上述声明与此类似,这就是你看到输出7 12的原因。

class Television {
   //The below code is essentially equal to your declaration of
   // private int channel = setChannel(7);
   private int channel;
   static{
       //This occurs before constructor call during class load.
       channel = setChannel(7);
   }
   ....
}

可以在Initializing Fields

上的java教程中找到更好的解释