1. ホーム
  2. .net

[解決済み] "メモリーリーク "の解剖学

2022-04-21 16:26:29

質問

.NETの観点で。

  • とは何ですか? メモリリーク ?
  • アプリケーションがリークしているかどうかは、どのように判断すればよいのでしょうか?どのような影響があるのでしょうか?
  • メモリリークを防ぐにはどうしたらよいですか?
  • アプリケーションでメモリリークが発生した場合、そのプロセスが終了したり、強制終了されたりすると、メモリリークは解消されるのでしょうか?それとも、アプリケーションのメモリーリークは、プロセス終了後もシステム上の他のプロセスに影響を及ぼしますか?
  • また、COM Interop や P/Invoke を介してアクセスされるアンマネージコードについてはどうでしょうか?

解決方法は?

私が見た中で一番良い解説は、無料の プログラミングの基礎」電子書籍 .

基本的には .NET メモリリークは、参照されているオブジェクトがルート化され、ガベージコレクションができなくなった場合に発生します。これは、意図した範囲を超えて参照を保持した場合に、偶然に発生します。

OutOfMemoryExceptionsが発生し始めたり、メモリ使用量が予想以上に増えたりすると、リークが発生していることがわかります( パフモン は素敵なメモリカウンターを備えています)。

理解する .NET のメモリモデルは、それを回避するための最良の方法です。具体的には、ガベージコレクタの仕組みと参照の仕組みを理解することです。また、よくある落とし穴として、おそらく最も一般的なのはイベントでしょう。もし、オブジェクト A のイベントに登録されています。 B であれば、オブジェクト A は、オブジェクト B が消えるのは B への参照を保持しています。 A . 解決策は、終了時にイベントの登録を解除することです。

もちろん、優れたメモリープロファイルを使えば、オブジェクトのグラフを見ることができ、オブジェクトのネストや参照を調べて、どこから参照されているのか、どのルートオブジェクトに責任があるのかを確認することができます ( 赤門蟻のプロファイル , JetBrains dotMemory, メムプロファイラ は本当に良い選択です。また、テキストのみの WinDbg SOS しかし、あなたが本当の第一人者でない限り、私は市販/ビジュアル製品を強くお勧めします)。

共有参照がガベージコレクタによって管理されていることを除けば、管理されていないコードはその典型的なメモリリークの影響を受けると私は考えています。この点については、間違っているかもしれません。