Javaでは、xを指す強い参照がなく、xがガベージコレクションに適格である場合、ガベージコレクトはオブジェクトxに対してfinalizeメソッドを呼び出します。 finalizeメソッドが決して終了しない場合、メモリリークが発生するでしょうか?Java:メモリリークを作成する定義済みのfinalizeメソッド
public class X{ protected void finalize(){ while(true){} } }
Javaでは、xを指す強い参照がなく、xがガベージコレクションに適格である場合、ガベージコレクトはオブジェクトxに対してfinalizeメソッドを呼び出します。 finalizeメソッドが決して終了しない場合、メモリリークが発生するでしょうか?Java:メモリリークを作成する定義済みのfinalizeメソッド
public class X{ protected void finalize(){ while(true){} } }
はい。
finalizeメソッドの内部でも、finalizeメソッドが呼び出されたオブジェクトに対して有効な参照を与えると、Javaはオブジェクトのガベージコレクションを行わず、finalizeメソッドを再度呼び出しません。
間違いなく。finalizeメソッドが返された後、メモリが割り当て解除されます。finalizeが返されない場合、momoryは割り当て解除されません。
ガベージコレクションで復活についてGoogleとあなたは
はい、それは、簡単には私が
を得たいくつかの時間後にpublic class X {
protected void finalize() {
while (true) {
}
}
public static void main(String[] args) throws Exception {
while (true) {
new X();
}
}
}
をテストすることになるfinalizeメソッドは、GCを保証するものではありません。さまざまなインスタンスを取得します
Exception: java.lang.OutOfMemoryError thrown from the UncaughtExceptionHandler in thread "main"
私がfinalize()を削除したとき、テストは決して止まらなかった。 JVMがOOMを行く前に、それは時間がかかること
ところでそれは
Exception in thread "main"
java.lang.OutOfMemoryError: Java heap space
at test.X.<init>(X.java:5)
at test.X.main(X.java:13)
GCを破るために、このテスト
public class X {
byte[] a = new byte[100 * 1000 * 1000];
protected void finalize() {
System.out.println();
}
public static void main(String[] args) throws Exception {
while (true) {
new X();
}
}
}
を実行するために十分だコメントを出し注意//System.out.println( );
これは、java.lang.ref.Finalizer $ FinalizerThread (The Secret Life Of The Finalizer)をブロックします。finalizeメソッドを実装するすべてのクラスのインスタンスは、java.lang.ref.Finalizer.ReferenceQueueでブロックされます。 'finalize'で新しいオブジェクトを作成し続けると、ファイナライズの実行を待っているオブジェクトがメモリを使い果たしてしまいます。ヒープ・ダンプを取ると、オブジェクトはjava.lang.ref.Finalizerによって保持されていることがわかります。以下の例を参照してください(実際のケースです)。
あなたはそれを試してみませんか? –