web-dev-qa-db-ja.com

「オンヒープ」と「オフヒープ」の違い

Ehcache オンヒープおよびオフヒープメモリ。違いはなんですか?それらを構成するためにどのJVM引数が使用されますか?

126
Synesso

ヒープ上のストアは、Javaヒープに存在する(およびGCの対象となる)オブジェクトを参照します。一方、オフヒープストアは、EHCacheによって管理されているが、ヒープの外部に格納されている(また、GCの対象ではない)(シリアル化された)オブジェクトを指します。オフヒープストアは引き続きメモリ内で管理されるため、オンヒープストアよりも若干遅くなりますが、ディスクストアよりも高速です。

オフヒープストアの管理と使用に関係する内部の詳細は、質問に投稿されたリンクではあまり明確ではないため、 Terracotta BigMemory の詳細を確認することをお勧めします。オフディスクストアの管理に使用されます。 BigMemory(オフヒープストア)は、数メガバイトまたはギガバイトのサイズのヒープでのGCのオーバーヘッドを回避するために使用されます。 BigMemoryは、他のネイティブJavaオブジェクトとは異なり、GCの影響を受けない direct ByteBuffers を介して、JVMプロセスのメモリアドレス空間を使用します。

151
Vineet Reynolds

from http://code.google.com/p/fast-serialization/wiki/QuickStartHeapOff

ヒープオフローディングとは?

通常、割り当てる非一時オブジェクトはすべて、Javaのガベージコレクターによって管理されます。 VMはガベージコレクションを行うための適切な作業を行いますが、特定の時点でVMはいわゆる「フルGC」を実行する必要があります。完全なGCでは、割り当てられたヒープ全体をスキャンします。つまり、GCの一時停止/スローダウンは、アプリケーションのヒープサイズに比例します。だから、「メモリは安い」と言っている人を信用しないでください。 Javaでは、メモリ消費によりパフォーマンスが低下します。さらに、1 GBを超えるヒープサイズを使用すると、顕著な一時停止が発生する場合があります。クラスターまたはグリッドでJavaプロセスが応答しなくなり、クラスターからドロップされる可能性があるため、リアルタイムに近いものがある場合、これは厄介なことがあります。

しかし、今日のサーバーアプリケーション(肥大化したフレームワークの上に頻繁に構築される;-))は、4Gbをはるかに超えるヒープを簡単に必要とします。

これらのメモリ要件に対する1つの解決策は、オブジェクトの一部を非Javaヒープ(OSから直接割り当てられる)に「オフロード」することです。幸いなことに、Java.nioは、「管理されていない」メモリチャンク(メモリマップファイルを含む)を直接割り当て/読み書きするクラスを提供します。

したがって、大量の「管理されていない」メモリを割り当て、これを使用してそこにオブジェクトを保存できます。任意のオブジェクトをアンマネージメモリに保存するための最も実行可能なソリューションは、シリアル化の使用です。これは、アプリケーションがオブジェクトをオフヒープメモリにシリアル化することを意味します。後でオブジェクトを逆シリアル化を使用して読み取ることができます。

Java VMによって管理されるヒープサイズは小さく保つことができるため、GCの一時停止はミリ秒単位で、誰もが満足し、仕事は完了です。

このようなオフヒープバッファーのパフォーマンスは、主にシリアル化の実装のパフォーマンスに依存することは明らかです。朗報:何らかの理由でFSTのシリアル化はかなり高速です:-)。

サンプル使用シナリオ:

  • サーバーアプリケーションのセッションキャッシュ。メモリマップファイルを使用して、ギガバイトの(非アクティブな)ユーザーセッションを保存します。ユーザーがアプリケーションにログインすると、データベースを扱うことなく、ユーザー関連のデータにすばやくアクセスできます。
  • 計算結果のキャッシュ(クエリ、htmlページなど)(計算が結果オブジェクトofcの逆シリアル化よりも遅い場合にのみ適用可能)。
  • メモリマップファイルを使用した非常にシンプルで高速な永続化

編集:一部のシナリオでは、ConcurrentMarkAndSweepやG1などのより洗練されたガベージコレクションアルゴリズムを選択して、より大きなヒープをサポートできます(ただし、16GBヒープを超える制限もあります)。改善された「一時停止」GC(Azul)が利用可能な商用JVMもあります。

83
R.Moeller

ヒープは、動的に割り当てられたオブジェクトが存在するメモリ内の場所です。 newを使用した場合、ヒープ上にあります。これは、関数スタックが存在するスタックスペースとは対照的です。ローカル変数がある場合、その参照はスタック上にあります。 Javaのヒープはガベージコレクションの対象であり、オブジェクトは直接使用できます。

EHCacheのオフヒープストレージは、通常のオブジェクトをヒープから取り出し、シリアル化し、EHCacheが管理するメモリチャンクにバイトとして格納します。ディスクに保存するようなものですが、まだRAMにあります。オブジェクトはこの状態では直接使用できません。最初にシリアル化解除する必要があります。また、ガベージコレクションの対象ではありません。

34
Adam

短い写真で

Java On/Off Heap storage in short

picクレジット


詳細写真

Java On/Off Heap storage in details

picクレジット

14
mrsrinivas

JVMはオフヒープメモリについて何も知りません。 Ehcacheは、ディスク上のキャッシュとメモリ内のキャッシュを実装しています。

1
gatkin

100%ではありません。ただし、ヒープは、Java自体またはehcache自体からの可能性が高い機能のいずれか、およびオフヒープのコードの機能に組み込まれたオブジェクトまたは割り当てられたスペースのセット(RAM上)のように聞こえますRamも独自のシステムです。ただし、これは整理されていないため、1桁遅いようです。つまり、ヒープ(RAMの1つの長いセットを意味する)を使用しない可能性があり、代わりに異なるアドレススペースを使用して、わずかに効率が低下する可能性があります。

それからもちろん、次のティアはハードドライブのスペースそのものです。

私はehcacheを使用していないので、あなたは私を信用したくないかもしれませんが、それは私が彼らのドキュメントから集めたものです。

1
msj121