2012-06-12 5 views
10

私は長いGCサイクルを持っています。チェックからの ヒープの古い(古い)領域にオブジェクトが多すぎることがわかりました。 ヒープのどの領域にオブジェクトがあるか、またはこれらのオブジェクトに関する静的な情報があるかどうかを知るための有益な情報がありますか?
私はSun/Oracle HotSpot JVM(Java 6)を使用しています。には、どのオブジェクトがヒープの「古い」領域にあるのかを知る方法があります。

EDIT:私の問題についてもう少し詳細:
私は大きなヒープ(32ギガバイト)を持っており、それは、ヒープの古い領域がGCを手動で15秒ののポーズを作る実行している、唯一の30%満杯の場合でも同じように見えます。どのオブジェクトを最適化するかを知るために、どのオブジェクトが古い領域に残っている「生存者」であるかを知りたい。

+1

[Visualvm](http://docs.oracle.com/javase/6/docs/technotes/guides/visualvm/intro.html)、[Visualgc](http://java.sun。 com/performance/jvmstat/visualgc.html)および[Jconsole](http://docs.oracle.com/javase/1.5.0/docs/guide/management/jconsole.html#gc)を参照してください。私は、これらのどれにもテニュアされたオブジェクトをリストすることはできないと思います。彼らはあなたには、しかし、いくつかの統計を与えます。だから私はこの記事をお勧めしますhttp://java.sun.com/docs/hotspot/gc/index.htmlそして+1 – bpgergo

+0

あなたのJVMスタートアップパラメータの完全なセットは何ですか? – moodywoody

答えて

7

私は現在の世代のJVMで動作するツールやユーティリティについては気づきません。

しかし、このようなユーティリティがどのように役立つかわかりません。

ヒープがいっぱいになっているため、長いGC時間が通常発生します。ヒープが100%いっぱいに近づくにつれて、GCで費やされる時間は指数関数的に増加する傾向があります。最悪の場合、ヒープは完全に塗りつぶされ、アプリケーションはOutOfMemoryErrorになります。 2つの解決方法があります

  • 根本的な原因は、ヒープが(アプリケーションが解決しようとしている問題の大きさのために)小さすぎるということであれば、ヒープサイズを増やすか、見ていずれかの方法のためにアプリケーションの作業セットを減らす。計算中に「生きて」いる必要があるオブジェクトの数/サイズである。

  • 根本原因がメモリリークの場合は、それを見つけて修正してください。

どちらの場合も、メモリプロファイラを使用すると、問題の分析に役立ちます。しかし、どのオブジェクトが古い世代であるかを知る必要はありません。問題の根本的な原因または問題の解決には関係ありません。最適化するために、どのオブジェクトを作成知るために


私は、古い地域に残っている「生存者」であるオブジェクトを知りたいです。

これは少し意味があるようになっています。ある空間がどこに住んでいるのではなく、どのオブジェクトが長命であるかを知る必要があるように思えます。jhatを使用してヒープスナップショットのシーケンスを比較することで可能です。 (良い方法があるかもしれません...)

しかし、私はまだこのアプローチが助けになるとは思わない。問題は、完全なGCがすべての到達可能な(ハード、ソフト、弱い、ファントム)オブジェクトをトラバースする必要があることです。また、30Gフルの32Gbヒープがある場合は、マーク/スイープ/リロケートするためのオブジェクトがまだたくさんあります。私は、ソリューションは、同時コレクタを使用し、アプリケーションのオブジェクト割り当て率に追いつくことができるようにチューニングすることが考えられます。

コードから直接System.gc()に電話しているようですが、 しないでください!System.gc()を呼び出すと、通常、JVMはフルガベージコレクションを実行します。それはかなりあなたに一時停止を保証されています。コレクタをいつ実行するかを決定するためには、JVMを離れる方がよいでしょう。

最後に、「オブジェクトの最適化」という言葉が何であるかは不明です。あなたはオブジェクト作成率を下げることを意味しますか?または、長寿命(キャッシュされたオブジェクト)の保持を管理するために何かを考えていますか?

0

私は、特定の世代のオブジェクトを「探索」できるツールを見たことがありません。

私はNetbeans Profilerに慣れています。あなたが求めていることを本当に行うことはできませんが、間違っていることのアイデアを伝えるツールがあります。

プロファイラでアプリケーションを実行し、Memoryを選択し、次にLive Resultsに列Generationsを選択します。 各オブジェクトの世代は教えてませんが、Surviving Generationsの番号が与えられます。したがって、数値が1より大きい場合は、テナント(おそらく生存者空間)にあるの数値が常に増加し、メモリリークが発生する場合はとなります。

0

私は、世代が異なる世代のオブジェクトについては何も教えてくれないユーティリティはないと思います。

  1. 片道です.jdkに付属のjconsoleを使用できます。 jconsoleの助けを借りてアプリケーションに接続し、すべての世代を監視することができます。ここではわかりません。
  2. 他の方法では、jmapを使用してダンプを取り、eclipse MATツールを使用して解析することができます。
  3. それとも、以下JVM引数を指定してアプリケーションを実行することができますし、私はそれがあなたの役に立つかもしれないと思うGCの

GC logging is enabled using JVM arguments; below are the arguments I use. (Note: the log file specified as file is reset each time the VM starts.

-verbose:gc -Xloggc:file

についての情報を持っているログインチ

1

ツールの象のトラックは、オブジェクトの作成と削除をプロファイルできます。elephantTrack。これにより、どのような種類のオブジェクトが予想より長く生存するかを知ることができ、メソッドの履歴では正確なオブジェクトを取得することができます。

しかし、大きなヒープは非常に長いプロファイル時間と非常に大きなプロファイルファイルを意味します。

+0

しかし... Webサイトによると、Java 1.7と(おそらく)それ以降のバージョンでは動作しません。 –

関連する問題