16

現在、実行中の Java アプリケーションを Visual VM で監視しています: http://visualvm.java.net/

-Xmx128m でメモリ使用量を強調しています。

実行すると、(予想どおり) ヒープ サイズが 128m に増加しますが、Java ヒープ スペース エラーが発生する前に、使用されるヒープは約 105m に収束します。

ここに画像の説明を入力

これらの残りの 20m が使用されないのはなぜですか?

4

3 に答える 3

5

ガベージ コレクターの人間工学に関する重要な事実を理解する必要があります。

ガベージ コレクションのコストのかかる部分は、ガベージではないオブジェクトを見つけて処理することです。

つまり、ヒープが最大容量に近づくにつれて、GC は回収されたスペースでのリターンがますます少なくなるために、ますます多くの時間を費やします。GC がメモリの最後のバイトをすべて使用しようとした場合、JVM はガベージ コレクションにますます多くの時間を費やすことになり、最終的には... 有用な作業がほとんど行われなくなります。

この異常な状況を回避するために、JVM は GC と有用な作業に費やされる時間の比率を監視します。比率が構成可能なしきい値を超えると、OutOfMemoryError(技術的には) 使用可能な空きメモリがある場合でも、GC は ... を発生させます。これはおそらくあなたが見ているものですが、他の説明も同様にもっともらしいです.

JVM オプションを介して GC しきい値、世代サイズなどを変更できますが、変更しない方がよいでしょう。アプリケーションのメモリ使用量が増え続けている理由を突き止めることをお勧めします。ほとんどの場合、これを引き起こしているコードにメモリ リーク、つまりバグがあります。すべてのメモリを使用していない理由を心配するのではなく、これらのバグを見つけて修正することに労力を費やしてください。

(実際、あなたはそれを使用しています...しかし、常にではありません。)

于 2011-05-04T11:53:12.447 に答える
4

ヒープは、Young-Generation(Eden-Space、および通常FromとToと呼ばれる同じサイズの2つのSurvivor-Spaces)、Old Generation(Tenured)、およびPermanentSpaceに分割されます。

このXmx/Xmsオプションは、全体的なヒープサイズを設定します。したがって、リージョン(デフォルトサイズ)は実際にはパーマネントスペースです-おそらく、ストレステストの詳細がわからないため、オブジェクトが実際にエデンからテニュアまたはパーマネントに移動されることはないため、エデンがなくなるまでこれらのリージョンは空のままになりますスペースの。

于 2011-05-04T11:28:32.207 に答える
4

Java はメモリを世代に分割します。Tenured 世代がいっぱいになると、ヒープ領域エラーが発生する可能性があります。通常、サイズは動的に変更されますが、固定サイズを設定した場合は変更されません。

于 2011-05-04T11:14:52.247 に答える