为什么不初始化本地final
变量编译?此行为似乎与final
字段形成对比,其中未初始化a会产生编译错误。
class Test {
final Test test1; // doesn't compile
public Test(){
final Test test2; // does compile
}
}
这种选择背后的逻辑是什么?
答案 0 :(得分:2)
这来自JLS的规则。
来自4.12.4
如果分配了最终变量,那么这是一个编译时错误,除非在分配之前它是明确未分配的(第16段)。
来自4.12.5
局部变量(§14.4,§14.14)必须在使用前通过初始化(§14.4)或赋值(§15.26)显式赋予值,其方式可以使用明确规则进行验证任务(§16)。
来自8.3.1.2
必须在声明它的类的每个构造函数(第8.8节)的末尾明确赋值空白的最终实例变量(第16.9节);否则会发生编译时错误。
因此,技术上的原因是因为它不是被禁止的。必须在构造对象时初始化字段。局部变量只需在使用之前进行初始化。
它背后的逻辑是类变量可能从另一个对象引用,因此需要在另一个对象可能具有初始化引用的时候初始化它。但是局部变量不会逃避它的范围,因此编译器可以保证只要它没有在该范围内使用它就不会被引用。