1
我剛剛注意到了一些關於for循環性能的問題,似乎是面對Google Android團隊給出的建議。請看下面的代碼:For-Loop性能Oddity
package com.jackcholt;
import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
public class Main extends Activity {
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
loopTest();
finish();
}
private void loopTest() {
final long loopCount = 1228800;
final int[] image = new int[8 * 320 * 480];
long start = System.currentTimeMillis();
for (int i = 0; i < (8 * 320 * 480); i++) {
image[i] = i;
}
for (int i = 0; i < (8 * 320 * 480); i++) {
image[i] = i;
}
Log.i("loopTest", "Elapsed time (recompute loop limit): " + (System.currentTimeMillis() - start));
start = System.currentTimeMillis();
for (int i = 0; i < 1228800; i++) {
image[i] = i;
}
for (int i = 0; i < 1228800; i++) {
image[i] = i;
}
Log.i("loopTest", "Elapsed time (literal loop limit): " + (System.currentTimeMillis() - start));
start = System.currentTimeMillis();
for (int i = 0; i < loopCount; i++) {
image[i] = i;
}
for (int i = 0; i < loopCount; i++) {
image[i] = i;
}
Log.i("loopTest", "Elapsed time (precompute loop limit): " + (System.currentTimeMillis() - start));
}
}
當我運行這段代碼我得到的logcat輸出如下:
I/loopTest( 726): Elapsed time (recompute loop limit): 759
I/loopTest( 726): Elapsed time (literal loop limit): 755
I/loopTest( 726): Elapsed time (precompute loop limit): 1317
正如你可以看到,似乎重新計算在每次迭代循環界限值的代碼的循環與使用文字值作爲循環限制的代碼非常相稱。但是,使用包含循環限制的預計算值的變量的代碼比其他任何一個都要慢得多。我並不感到驚訝的是,訪問變量應該比使用文字更慢,但爲什麼看起來像它的代碼應該在循環的每次迭代中使用兩條乘法指令,因此在性能上與文字相當?
難道是因爲文字是唯一倍增,Java編譯器正在優化乘法和使用預先計算的文字?