51

次のオプションを使用したインタビューで、この質問に遭遇しました。

Javaでオブジェクトを破棄する方法は?

a. System.gc();  
b. Runtime.getRuntime.gc();  
c. object.delete();  
d. object.finalize();  
e. Java performs gc by itself, no need to do it manually.
  1. 答えはeである必要がありますか?

  2. eがなかったらどうしますか?それから ?明らかにcは答えではありません。aとbは、アプリケーション全体に対してgcを実行します(質問には1つのオブジェクトが必要です)。finalize()がgcの直前に呼び出されるため(ただし、finalizeの後にgcが呼び出される必要がありますか?)、それとも間違っているので、dだと思います。eはこの質問に答えるためにそこにいなければなりませんか?

4

6 に答える 6

66

回答Eは正解です。Eがない場合は、すぐにメモリが不足します(または)正解はありません。

GCの対象となるには、オブジェクトに到達できない必要があります。JVMは、複数のスキャンを実行し、オブジェクトをある世代から別の世代に移動して、GCの適格性を判断し、オブジェクトに到達できない場合にメモリを解放します。

于 2012-11-03T03:53:53.473 に答える
39

他の回答が機能しない理由を明確にするには:

  1. System.gc()(とRuntime.getRuntime().gc()、まったく同じことをします)あなたがものを破壊したいというヒント。漠然と。JVMは、GCサイクルの必要性を認識していない場合、GCサイクルを実行する要求を自由に無視できます。さらに、オブジェクトへの到達可能な参照をすべて無効にしない限り、GCはオブジェクトにアクセスしません。したがって、AとBは両方とも失格となります。

  2. Runtime.getRuntime.gc()悪い文法です。getRuntime関数であり、変数ではありません。それを呼び出すには、その後に括弧が必要です。したがって、Bは二重失格となります。

  3. Object方法はありませんdelete。したがって、Cは失格となります。

  4. Object メソッドはありますが、何も破壊しませfinalizeん。 ガベージコレクターだけが実際にオブジェクトを削除できます。 (そして、多くの場合、彼らは技術的にそれをすることさえしません;彼らは他の人をするときにそれをコピーしないので、それは取り残されます。)すべてはオブジェクトに前finalizeクリーンアップする機会を与えることです。 JVMはそれを破棄します。さらに、直接電話をかけることは絶対にしないでください。(保護されているため、JVMではとにかく任意のオブジェクトで呼び出すことはできません。)したがって、Dは失格となります。finalizefinalize

  5. それに加えて、object.doAnythingAtAllEvenCommitSuicide()実行中のコードにへの参照がある必要がありますobject。それだけで「生きている」ため、ガベージコレクションの対象外になります。したがって、CとDは二重に失格となります。

于 2012-11-03T04:16:59.683 に答える
19

短い答え-E

E残りは明らかに間違っているという答えが与えられていますが、..

長い答え-それはそれほど単純ではありません。場合によります ...

単純な事実として、ガベージコレクターは、メモリの負荷が非常に高い場合を除いて、収集の実行可能な候補であるすべてのオブジェクトをガベージコレクションすることを決定することはありません。そして、Javaは他の言語と同じようにメモリリークの影響を受けやすく、原因となるのが難しいため、発生したときに見つけるのが難しいという事実があります。

次の記事には、メモリ管理がどのように機能し、機能しないか、そして何が何によって取り上げられるかについての多くの良い詳細があります。世代別ガベージコレクターの動作メモリへの感謝(WindowsおよびLinuxでJVMがネイティブメモリをどのように使用するかを理解する)

リンクを読むと、Javaでのメモリ管理は多肢選択式の質問ほど単純ではないことがわかると思います。

于 2012-11-03T04:09:54.663 に答える
10

nullに設定します。その後、参照はなくなり、オブジェクトはガベージコレクションの対象になります。GCはオブジェクトをヒープから自動的に削除します。

于 2016-10-30T00:26:39.740 に答える
4

コードは次のとおりです。

public static void main(String argso[]) {
int big_array[] = new int[100000];

// Do some computations with big_array and get a result. 
int result = compute(big_array);

// We no longer need big_array. It will get garbage collected when there
// are no more references to it. Since big_array is a local variable,
// it refers to the array until this method returns. But this method
// doesn't return. So we've got to explicitly get rid of the reference
// ourselves, so the garbage collector knows it can reclaim the array. 
big_array = null;

// Loop forever, handling the user's input
for(;;) handle_input(result);
}
于 2016-04-28T12:33:23.803 に答える
0

Javaでは、ガベージコレクションを行う明示的な方法はありません。JVM自体は、参照を持たないオブジェクトをチェックするバックグラウンドでいくつかのスレッドを実行します。これは、オブジェクトにアクセスするすべての方法が失われることを意味します。一方、オブジェクトを作成したプログラムが終了または終了したスコープを超えた場合、オブジェクトはガベージコレクションの対象にもなります。あなたの質問に来ると、メソッドfinalizeはC++のデストラクタと同じです。finalizeメソッドは、実際には、JVMによってオブジェクトメモリをクリアする直前に呼び出されます。プログラムでfinalizeメソッドを定義するかどうかはあなた次第です。ただし、プログラムの終了後にオブジェクトのガベージコレクションが実行された場合、JVMはプログラムで定義したfinalizeメソッドを呼び出しません。ファイナライズメソッドの使用は何ですか?たとえば、外部ファイルへのストリームを必要とするオブジェクトを作成し、このオブジェクトにfinalizeメソッドを明示的に定義して、ファイルに対してストリームが開かれているかどうかを確認し、開かれていない場合はストリームを閉じているとします。数行のコードを記述した後、オブジェクトへの参照を失ったとします。その後、ガベージコレクションの対象になります。JVMがオブジェクトのスペースを解放しようとしているとき、JVMはfinalizeメソッドを定義したかどうかをチェックし、メソッドを呼び出すだけなので、ストリームが開かれるリスクはありません。ファイナライズメソッドは、プログラムをリスクフリーでより堅牢にします。

于 2017-03-19T15:38:57.260 に答える