4

まとめ:

本来よりも多くのメモリを消費するアプリケーションがあります (予想量の約 250%) が、メモリ リークを見つけることができないようです。同じ関数 (多くの割り当てを行う) を呼び出すと、メモリ使用量がある程度増加し続け、その後は変化せず、そこにとどまります。

プログラムの詳細:

アプリケーションは、四分木データ構造を使用して「ポイント」を保存します。メモリに格納するポイントの最大数 (キャッシュ サイズ) を指定することができます。「ポイント」は「PointBuckets」(クワッドツリーのリーフ ノードにリンクされたポイントの配列) に格納され、クワッドツリー内のポイントの最大総数に達すると、シリアル化されて一時ファイルに保存され、次のときに取得されます。必要です。これはすべてうまくいくようです。

ファイルが読み込まれると、新しい Quadtree が作成され、古いものが存在する場合は削除され、ファイルからポイントが読み取られ、Quadtree に 1 つずつ挿入されます。ノード分割などでバケットが作成および削除されると、大量のメモリ割り当てが発生します。

症状:

300MB のメモリを 1 回使用すると予想されるファイルをロードすると、予想される量のメモリが消費されます。すべて良い。同じファイルを何度もロードし続けると、メモリ使用量が増加し続けます (Linux の一番上の RES 列を見ています) 約 700MB まで増加します。これは、メモリ リークを示している可能性があります。ただし、ファイルをロードし続けると、メモリ消費量は 700MB のままです。

別のこと: valgrind massif を使用してメモリ使用量を確認すると、常に予想される制限内に収まっています。たとえば、キャッシュ サイズを 1.5 GB に指定してプログラムを単独で実行すると、最終的に 4 GB のメモリが消費されます。Massif で実行すると、常に 2GB 未満に留まり、生成されたグラフでは、実際には予想される 1.5GB を超えて割り当てられていないことがわかります。私の素朴な仮定は、massif が何らかの方法で断片化を防止するカスタム メモリ プールを使用するために発生するということです。

それで、ここで何が起こっていると思いますか?メモリの断片化である場合、この問題を解決するにはどのような解決策を探す必要がありますか?

4

1 に答える 1

3

単純なアロケーターと OS のキャッシュ動作について説明します。解放するのではなく、割り当てたメモリを保持するため、次に要求したときに、より迅速な方法でメモリを返すことができます。ただし、250% は、この種の効果にはかなりの量のように聞こえます。断片化の問題が発生している可能性があります。

オブジェクト プールやメモリ アリーナなどの断片化のないアロケーターにアロケーターを交換してみてください。

于 2012-07-11T17:25:19.350 に答える