我在最终变量的分配中遇到了一些奇怪的行为.您可以在构造函数中指定最终变量来初始化它,这是有道理的.但是,即使最终变量是子类的成员,您也无法在子类中执行相同操作 -
public class FinalTest {
public final String name;
public FinalTest()
{
name = "FinalTest";
}
public static class FinalTestSubclass extends FinalTest {
public FinalTestSubclass()
{
name = "FinalTestSubclass"; //<---- this won't compile, assignment to final variable.
}
}
}
Run Code Online (Sandbox Code Playgroud)
有人会想到这个应该/会以这种方式运作的一个很好的理由吗?
eri*_*son 11
子类的每个构造函数都必须调用超类的构造函数作为其第一个操作.必须在构造函数完成之前初始化每个最终成员变量.最终变量只能分配一次.根据这些规则,子类构造函数不可能直接将值赋给final超类的成员.
制造例外将增加复杂性并创建"陷阱"以换取有限的额外效用.
一个实际的解决方案是提供一个超类构造函数,它将值赋给最终成员.protected如果需要,这可以是包或私有的.如果超类超出了你的控制范围,那么允许派生类打破其成员最终性的假设很有可能会导致其他问题.
如果允许您为其分配值name,FinalTestSubClass则意味着分配的值FinalTest实际上不是最终值.
如果你的例子是有效的,那么这意味着name可能有不同的值(基于实例化的类),使得final修饰符非常多余.
一个更好的问题是,为什么要允许你想要的行为?