JLS によると、int
配列は初期化直後にゼロで埋められるべきです。しかし、そうではない状況に直面しています。このような動作は、JDK 7u4 で最初に発生し、その後のすべての更新でも発生します (私は 64 ビット実装を使用しています)。次のコードは例外をスローします。
public static void main(String[] args) {
int[] a;
int n = 0;
for (int i = 0; i < 100000000; ++i) {
a = new int[10];
for (int f : a)
if (f != 0)
throw new RuntimeException("Array just after allocation: "+ Arrays.toString(a));
Arrays.fill(a, 0);
for (int j = 0; j < a.length; ++j)
a[j] = (n - j)*i;
for (int f : a)
n += f;
}
System.out.println(n);
}
-Xint
例外は、JVM がコード ブロックのコンパイルを実行した後に発生し、フラグでは発生しません。さらに、このArrays.fill(...)
ステートメントは (このコードの他のすべてのステートメントと同様に) 必要であり、それがなくても例外は発生しません。このバグの可能性は、JVM の最適化に限定されていることは明らかです。そのような行動の理由についてのアイデアはありますか?
更新:
Gentoo Linux、Debian Linux (両方ともカーネル 3.0 バージョン)、および MacOS Lion 上の HotSpot 64 ビット サーバー VM、Java バージョン 1.7.0_04 から 1.7.0_10 でこの動作が見られます。このエラーは、上記のコードでいつでも再現できます。この問題は、32 ビット JDK または Windows ではテストしていません。私は既に Oracle にバグ レポート (バグ ID 7196857) を送信しており、公開されている Oracle バグ データベースに数日で表示される予定です。
更新:
Oracle は、公開バグ データベースでこのバグを公開しました: http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=7196857