【发布时间】:2022-01-28 04:04:01
【问题描述】:
我看到有人说在迭代时将 size 的值缓存为列表或将 length 的值缓存为数组,以节省反复检查长度/大小的时间。
所以
for (int i = 0; i < someArr.length; i++) // do stuff
for (int i = 0; i < someList.size(); i++) // do stuff
会变成
for (int i = 0, length = someArr.length; i < length; i++) // do stuff
for (int i = 0, size = someList.size(); i < size; i++) // do stuff
但是既然Array#length不是一个方法,只是一个字段,应该没有区别吧?如果使用 ArrayList,size() 只是一个 getter,那么这两种方法不应该也是一样的吗?
【问题讨论】:
-
我认为性能损失可以忽略不计,但我希望能解释一下
-
@VGR 你一开始就不想以这种方式迭代 LinkedList。
i会做什么?每次迭代都要遍历整个列表直到i? -
@VGR
LinkedList将大小存储在字段中,就像ArrayList一样。所以size()方法在以这种方式迭代LinkedList时不是问题...... -
@user16320675
array.length永远不会改变。它看起来像一个字段访问,但实际上并非如此。有一个专用的字节码指令,arraylength用于获取长度,但根本无法更改以更改数组长度。 -
@user16320675 如果
someArr更改,您想要使用更改后的someArr.length,因为仅使用相应的长度可以保证您保持在范围内。这对优化器有真正的影响,因为这在为边界检查生成额外代码或依赖循环永远不会超出边界的已知不变量之间产生差异。这意味着您每次使用length = someArr.length或访问someArr.length都没有关系;重要的是,JIT/HotSpot 优化器是否可以证明someArr在任何一种情况下都不会改变。
标签: java arrays performance for-loop arraylist