为什么最终变量不总是常量表达式?
Why isn't a final variable always a constant expression?
在下面的代码中:
final int a;
a=2;
byte b=a; // error: possible loss of precision
为什么会出现此错误? a
final 变量不是编译时常量表达式,因此在赋值期间隐式缩小为字节吗?
换句话说,上面的代码不等同于:
final int a=2;
byte b=a;
来自JLS
A blank final
is a final
variable whose declaration lacks an initializer.
A constant variable is a final
variable of primitive type or type
String
that is initialized with a constant expression (§15.28).
你的变量
final int a;
是一个 空白 final
变量。它缺少初始化程序。第二段不适用于它,因为它没有在声明时初始化。因此它不是常量表达式。
这也适用于字段。
因为 final 变量可以延迟初始化,编译器无法确定 b 在 case 分支中有值。
编译器没那么聪明。
我们可以看出该值将始终为 2。但是如果我们有这样的东西呢?
class ABC{
final int a;
public ABC(){
if(Math.random() < .5){
a = 2;
}
else{
a = 12345;
}
byte b = a;
}
}
编译器不够智能,无法区分这两种情况,因此它会报错。
在下面的代码中:
final int a;
a=2;
byte b=a; // error: possible loss of precision
为什么会出现此错误? a
final 变量不是编译时常量表达式,因此在赋值期间隐式缩小为字节吗?
换句话说,上面的代码不等同于:
final int a=2;
byte b=a;
来自JLS
A blank
final
is afinal
variable whose declaration lacks an initializer.A constant variable is a
final
variable of primitive type or typeString
that is initialized with a constant expression (§15.28).
你的变量
final int a;
是一个 空白 final
变量。它缺少初始化程序。第二段不适用于它,因为它没有在声明时初始化。因此它不是常量表达式。
这也适用于字段。
因为 final 变量可以延迟初始化,编译器无法确定 b 在 case 分支中有值。
编译器没那么聪明。
我们可以看出该值将始终为 2。但是如果我们有这样的东西呢?
class ABC{
final int a;
public ABC(){
if(Math.random() < .5){
a = 2;
}
else{
a = 12345;
}
byte b = a;
}
}
编译器不够智能,无法区分这两种情况,因此它会报错。