我的java类
private static final String constantString = "Constant";
private static final Integer constantInteger = 5;
public static void main(String[] args) {
String s2 = constantString + "append"; // LINENUMBER 9
Integer i2 = constantInteger + 7; // LINENUMBER 10
}
Run Code Online (Sandbox Code Playgroud)
字节码
LINENUMBER 9 L0
LDC "Constantappend"
ASTORE 1
L1
LINENUMBER 10 L1
GETSTATIC TestClass.constantInteger : Ljava/lang/Integer;
INVOKEVIRTUAL java/lang/Integer.intValue()I
BIPUSH 7
IADD
Run Code Online (Sandbox Code Playgroud)
问题1:为什么编译器没有用5代替最终的Integer(constantInteger)值,但是对于String它做了!
如果删除Integer变量的final关键字
java代码:
private static Integer constantInteger = 5;
Run Code Online (Sandbox Code Playgroud)
字节码:
LINENUMBER 10 L1
GETSTATIC TestClass.constantInteger : Ljava/lang/Integer;
INVOKEVIRTUAL java/lang/Integer.intValue()I
BIPUSH 7
Run Code Online (Sandbox Code Playgroud)
字节码在两种不同情况下是相同的(静态最终整数,静态整数)
问题2:那么使Integer最终有什么用?
猜测:原因是字符串实习.编译器实例化字符串并具有连接字符串连接的优化.但它没有实习数字,显然缺乏优化.
我想不出有什么理由不能优化整数情况,除了它还没有在编译器中实现.正如其他答案中所提到的,Integer +涉及装箱/拆箱操作,与字符串+及其隐式StringBuilder优化和实际逻辑完全不同.因此,如果查看,String +优化可能来自编译器实现点的"免费".
编译器不会注意到具有非null值的最终Integer必然是非null.所以它继续并将其拆箱.JIT编译器完全有可能在加工机器代码的过程中改进这一点; 对于应用程序的性能来说,这似乎不太可能.
'final'是关于语义,而不是表现.语言保证了语义; 性能完全是实现者的心血来潮.因此,明确地回答'问题#2':最后的要点是具有防止修改的语义.还要注意嵌入式匿名类的规则,它们只能使用最终的局部变量.
| 归档时间: |
|
| 查看次数: |
1625 次 |
| 最近记录: |