以下Java程序平均需要在0.50到0.55之间运行:
public static void main(String[] args) {
long startTime = System.nanoTime();
int n = 0;
for (int i = 0; i < 1000000000; i++) {
n += 2 * (i * i);
}
System.out.println((double) (System.nanoTime() - startTime) / 1000000000 + " s");
System.out.println("n = " + n);
}
Run Code Online (Sandbox Code Playgroud)
如果我更换2 * (i * i)用2 * i * i,它需要0.60〜0.65s之间运行.怎么会?
我运行了每个版本的程序15次,在两者之间交替.结果如下:
2*(i*i) | 2*i*i
----------+----------
0.5183738 | 0.6246434
0.5298337 | 0.6049722
0.5308647 | 0.6603363
0.5133458 | 0.6243328
0.5003011 | …Run Code Online (Sandbox Code Playgroud) 查看源代码java.util.OptionalInt,可选的int由a int value和a组成boolean isPresent.获取空的可选int的唯一方法是通过OptionalInt.empty()返回的方法OptionalInt.EMPTY,即所有空的可选int的公共实例.
如果是这种情况,那么为什么该isPresent()方法实现return isPresent而不是this == EMPTY通过删除isPresent字段来减少内存使用?
JVMS 说:
在Oracle对Java虚拟机的一些实现中,对类实例的引用是指向本身是一对指针的句柄的指针:一个指向包含对象方法的表的指针,以及指向表示对象的Class对象的指针对象的类型,另一个分配给从堆为对象数据分配的内存。
我不明白为什么引用会以这种方式实现,而不是使它们成为直接指向对象数据后的方法表指针的指针。这样可以避免在对象创建时分配额外的内存,而在字段访问时避免额外的指针取消引用。
Oracle如此实施它们的原因是什么?