Java实例变量初始化构造函数内外混淆

标签 java

让我们看一小段java代码

class Foo {
  int i = 0;
  int j;
  public Foo(int j){
     this.j = j;
  }
}

上面的示例展示了 Java 中初始化变量的两种方法。但我的问题是哪个变量首先被初始化?构造函数外部的变量还是构造函数内部的变量? 当我实例化上面的类 Foo foo = new Foo(5) 时,我知道该类的构造函数被调用,这意味着变量 j 首先被初始化。谁能帮我解释一下顺序。

最佳答案

优先级

在您的情况下,int j 首先发生并默认为 0,然后在调用构造函数来创建时重新分配给 5一个新实例。

j 仅在构造函数运行时才会重新分配。当您在构造函数之外为实例成员分配某些内容时,实例成员首先会被初始化。

执行顺序

每行代码都按照其出现的顺序执行。声明始终发生在构造函数之前,按照它们在代码中列出的顺序。

确定性和可预测性

您应该只在单个构造函数内的单个位置初始化实例成员。

依赖默认值会导致难以追踪错误,并使测试成为一场噩梦,但未分配的实例成员对于 IDE、编译器和运行时来说会很突出。不幸的是,对于像 int 这样的原语,它们默认为 0,这可能不是您想要/需要的。

更好的设计是:

 private final int j;

 public Foo(final int j) { this.j = j; }

这可以防止 j 在初始化时被分配任何内容,并且您永远不必担心它会发生变化。

关于Java实例变量初始化构造函数内外混淆,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21129340/

相关文章:

java - 试图将所有联系人放入 ListView 中?

java - 如何将ArrayList传递到本地数据库

java - 监控关键系统上的文件系统访问

java - 计算平均值或将 ArrayList 作为函数的参数

java - Jsoup.parse(String) 和 document.toString() 和 document.html() 不一样

java - 通用断言失败

javascript - Javascript 中的 RSA-OAEP 加密和 Java 中的解密

java - 获取有关 IP 地址的数据

java - 如何抑制Java类实例上的静态方法?

java - 具有空属性实例化策略的深度 bean 复制