98

プログラムのセットアップでのみ使用される架空のユーティリティ クラスがあるとします。

class MyUtils {
   private static MyObject myObject = new MyObject();
   /*package*/static boolean doStuff(Params... params) {
       // do stuff with myObject and params...
   }
}

myObject は、使用されなくなったときにガベージコレクションされますか、それともプログラムの存続期間中残りますか?

4

6 に答える 6

123

クラスのロード中は、静的変数をガベージ コレクションに選択できません。それらは、それぞれのクラスローダー (このクラスのロードを担当した) 自体がガベージとして収集されるときに収集できます。

JLS セクション 12.7 クラスとインターフェイスのアンロードを確認してください。

クラスまたはインターフェイスは、定義しているクラス ローダーがガベージ コレクターによって再利用される場合にのみアンロードできます [...] ブートストラップ ローダーによってロードされたクラスおよびインターフェイスはアンロードできません。

于 2009-01-17T09:44:14.597 に答える
61

静的変数は、ClassLoader によって参照される Class オブジェクトによって参照されます。そのため、ClassLoader が何らかの方法でクラスをドロップするか (それが可能な場合)、または ClassLoader 自体がコレクションの対象になる (より可能性が高い - Web アプリケーションのアンロードを考える) 場合を除き、静的変数 (またはむしろ、それらが参照するオブジェクト) は収集されません。

于 2009-01-17T09:33:21.763 に答える
14

一時オブジェクトを静的初期化に使用してから破棄する場合は、静的初期化ブロックを使用できます。

class MyUtils {
   static
   {
      MyObject myObject = new MyObject();
      doStuff(myObject, params);
   }

   static boolean doStuff(MyObject myObject, Params... params) {
       // do stuff with myObject and params...
   }
}

静的初期化ブロックは特殊な種類の静的メソッドであるため、myObjectはローカル変数であり、ブロックの実行が終了した後にガベージコレクションを行うことができます。

于 2009-01-17T18:49:44.370 に答える
7

これはあなたの質問に答えると思います-基本的に、クラスが特別なクラスローダーから来て、それがクラスをアンロードしない限り、そうではありません。

于 2009-01-17T09:12:24.503 に答える
0

ここで重要なのは、クラス インスタンス、つまりオブジェクトのガベージ コレクションです。ClassLoader インスタンスは、本質的にオブジェクトです。そのため、Classloader オブジェクトがガベージ コレクションされていない場合、ヒープに格納されたそれらの参照 (つまり、静的なもの) はほとんどガベージ コレクションされません。例外は String プールです。

だから、あなたが突然やろうと決心する前に private static MyGiantClass myGiantObject = new MyGiantClass() 、私が難しい方法を学んだので、よく考えてください.

于 2018-05-02T22:31:53.033 に答える