私のアプリケーションは物理シミュレーションを実行しているため、現在かなりのメモリを消費しています。問題は、一貫して、51回目のシミュレーションで、メモリのヒープ領域が原因でJavaがエラーをスローすることです(私のプログラムは最終的に数千のシミュレーションを実行します)。
とにかく、ヒープスペースを増やすだけでなく、プログラムを変更して、実行ごとにヒープスペースがクリアされ、任意の数のシミュレーションを実行できるようにできますか?
ありがとう
-編集-
みんなありがとう。シミュレーター・ソフトウェアは実行ごとに情報をクリアしていなかったことがわかり、それらの実行をすべてアレイリストに保存しました。
Java仮想マシンの起動時にヒープが割り当てられるため、ヒープをプログラムで動的に増やす方法はありません。
ただし、このコマンドは使用できます
Java -Xmx1024M YourClass
メモリを1024に設定するには
または、最小最大値を設定できます
Java -Xms256m -Xmx1024m YourClassNameHere
大量のメモリを使用していて、メモリリークに直面している場合は、多数のArrayList
sまたはHashMap
sを使用しているかどうかを確認する必要があります。
ArrayList
は、 動的配列 として実装されます。 Sun/Oracleのソースコードは、新しい要素が完全なArrayList
に挿入されると、元の配列の1.5倍のサイズの新しい配列が作成され、要素がコピーされることを示しています。つまり、ArrayList
メソッドを呼び出さない限り、使用する各trimToSize
のスペースの最大50%を浪費する可能性があります。または、事前に挿入する要素の数がわかっている場合は、引数として初期容量を指定してコンストラクターを呼び出します。
私はHashMap
のソースコードをあまり注意深く調べませんでしたが、一見すると、各HashMap
の配列の長さは2のべき乗でなければならず、動的配列の別の実装になります。 HashSet
は本質的にHashMap
のラッパーであることに注意してください。
この問題の診断に役立つさまざまなツールがあります。 JDKには JVisualVM が含まれています。これにより、実行中のプロセスにアタッチして、制御不能になっている可能性のあるオブジェクトを表示できます。 Netbeansにはラッパーがあり、かなりうまく機能します。 EclipseにはEclipse Memory Analyzerがあり、これは私が最も頻繁に使用するものですが、大きなダンプファイルを少しうまく処理しているようです。コマンドラインオプション -XX:+ HeapDumpOnOutOfMemoryError もあります。これは、プログラムがクラッシュしたときに基本的にプロセスメモリのスナップショットであるファイルを提供します。上記のツールのいずれかを使用して確認することができます。これらの種類の問題を診断する際に非常に役立ちます。
プログラムの動作の程度によっては、JVMがガベージコレクションの最適なタイミングを知らないという単純なケースである可能性があります。また、パラレルガベージコレクションのオプションも調べてください。
私も同じ問題に直面しました。次の手順に従ってビルドを実行することで解決しました。
->プロジェクトを右クリックして、RunAs->実行構成を選択します
プロジェクトをBaseDirectoryとして選択します。目標の代わりにEclipse:eclipseをインストールします
-> 2番目のタブで、VM引数として-Xmx1024mを指定します。
この問題は、一般的なJavaメモリリークに似ていることを付け加えます。
JVMガベージコレクターがJava/Java EEアプリケーションの「無駄」なメモリを時間をかけてクリアできない場合、 OutOfMemoryError:Java heap space が結果になります。
最初に適切な診断を実行することが重要です。
-Xmxを追加してメモリを増やしてみて(Java -Xmx1024M YourClass
)、必要のない変数の参照を忘れないようにしてください(メモリリーク)。
不要になった変数(以前のシミュレーションのデータなど)への参照を保持していますか?その場合、メモリリークが発生しています。どこでそれが起こっているのかを見つけて、変数が不要になったら変数への参照を削除することを確認する必要があります(変数がスコープ外になると自動的に発生します)。
メモリ内の以前のシミュレーションからのすべてのデータが実際に必要な場合は、ヒープサイズを増やすか、アルゴリズムを変更する必要があります。
Javaは、すべてのオブジェクトが参照されなくなったときに、ヒープスペースをクリアすることになっています。通常、OSに解放しませんが、内部で再利用するためにメモリを保持します。クリアされていないアレイなどがあるかどうかを確認してください。
いいえ。ヒープは、ガベージコレクターが気分に応じてクリアします。 (System.gc()
を使用して)実行するように要求できますが、実行が保証されるわけではありません。
最初に-Xmx256m
を設定してメモリを増やしてみてください