SHOEISHA iD

※旧SEメンバーシップ会員の方は、同じ登録情報(メールアドレス&パスワード)でログインいただけます

DeveloperZine(デベロッパージン)- エンジニアの意思決定を支える技術情報メディア ProductZine

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

特集記事

オブジェクトサイズの計測とメモリリークの検出

WebSphere Application Serverのチューニング 2

ヒープダンプの解析

 HeapAnalyzerを使うと、ヒープ内にあるオブジェクトをクラス名で検索することができます。例えば、WASのHttpSessionの実体は「MemorySessionData」というクラスです。このクラスをヒープダンプから検索します。検索クラス名は正規表現で入力します。

[Analysis]-[Search Name]→「.*MemorySessionData.*」と入力→[Find]
[Analysis]-[Search Name]→「.*MemorySessionData.*」と入力→[Find]

 検索結果が表示されます。このデータでは、セッションのサイズが1,792bytesであることが分かります。

各列の意味
列タイトル(左から)意味
TotalSize各オブジェクトのサイズです。このオブジェクトが子(属性、クラス変数)を持つ場合は、その子のサイズを含めた合計のサイズとなります。
Size子オブジェクトを含めない、オブジェクトそのもののサイズです。
No.Child子オブジェクトの数です。
Address参照アドレスです。同じクラスでも、別のインスタンスであればアドレスが異なります。
Objectクラス名が表示されます。先頭に「class」と表示される場合は、クラス定義のサイズとなります。クラス定義には、static宣言されたクラス変数のサイズが含まれます。

 では、このオブジェクトがどのような参照を持つかを調べてみましょう。

テーブルから調べたいオブジェクトを選択→[Find object in tree view]
テーブルから調べたいオブジェクトを選択→[Find object in tree view]

 ツリービューが開きます。この画面でオブジェクトの親子階層、それぞれのサイズを詳しく調べることができます。MemorySessionDataは、SessionSimpleHashMapの中にあることが分かります。

メモリリークの検出

 HeapAnalyzerはメモリリークの検出にも役立ちます。[Analysis]-[Search Name]で、調査したいクラスのパッケージ名の一部を正規表現で入力します。

.*jp/co/XXX.*

 パッケージ名で絞り込まれたオブジェクトの一覧が表示されます。この一覧からメモリリークを以下の方法で探索します。

  • サイズの大きなオブジェクトのツリーを調べる。
  • 起動時の一覧と、メモリリークを起こした状態での一覧を比較する。
  • 一覧の中で想定以上の数がインスタンスが生成されているオブジェクトを見つける。

 サイズや数が増加していればメモリリークの可能性があるので、ツリーを詳しく調査すれば、メモリリークを起こしたオブジェクトを特定できます。

セッションオブジェクトにコレクションを使う際は要注意!

 例えば、セッション内にユーザー情報を保持します。このようなとき、ユーザー情報をコレクションクラスに保持し、それを更にセッション内に保持するようなことは避けましょう。

セッションオブジェクトの悪い例:コレクションクラスを使う。
public class UserInfoBean {
    private Hashtable table;
    public String getUserName(){
        return table.get("username");
    }
}
セッションオブジェクトの良い例:POJOを使う。
public class UserInfoBean {
    private String userName;
    public String getUserName() {
        return username;
    }
}

 JavaBeanの形(POJO)ならば、サイズが必要最小限に抑えられます。

 コレクションクラスは、保持すべき情報そのもの以外にハッシュ領域を持つため、不必要にサイズが大きくなります。コレクションクラスを使う必然性がないのであれば、できるだけPOJOを使いましょう。

最後に

 以上、オブジェクトのサイズを計測する方法を説明しました。今までは感覚的に「大きい」「小さい」と言っていたサイズが正確に計測でき、問題点の解析、チューニングがやりやすくなります。また、メモリリークを簡単に観測できるようになります。

 これまで手探りでメモリリークを探していた方、ぜひお試しあれ!

参考資料

この記事は参考になりましたか?

連載通知を行うには会員登録(無料)が必要です。
既に会員の方はを行ってください。
特集記事連載記事一覧

もっと読む

この記事の著者

佐藤 龍之介(サトウ リュウノスケ)

某SIer にて、主にWeb系開発プロジェクトに従事。 趣味はラーメン食べ歩き。 

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

この記事は参考になりましたか?

この記事をシェア

CodeZine(コードジン)
https://codezine.jp/article/detail/1633 2007/09/03 14:00

イベント

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

新規会員登録無料のご案内

  • ・全ての過去記事が閲覧できます
  • ・会員限定メルマガを受信できます

メールバックナンバー