OpenGLゲームに小さなデバッグUIを追加したかったのですが、これはさまざまなデバッグオプション/出力表示で頻繁に更新されます。私が欲しかったのは、ガベージコレクターの各世代のアクティブオブジェクトを表示する定数カウンターでした。名前などは必要ありません。合計数だけです。ゲーム内で特定のことをするときに目が離せないもの。
しかし、私の問題は、さまざまな世代で現在生きているオブジェクトの総数を数える方法が見つからないように見えることです。
すべてのコンストラクター内でインクリメントされ、クラスファイナライザー内でデクリメントされるグローバル静的フィールドを保持することも検討しました。ただし、これには、前述の機能をすべてのクラスに手動でコーディングする必要があり、「世代ごとの合計」の問題は解決されません。
私がこれをどうやってやるのか知っていますか?
(質問のタイトル:) 「ガベージコレクションのためにキューに入れられたオブジェクトの総数を数える」
(質問の本文から:) 「しかし、私の問題は、さまざまな世代で現在生きているオブジェクトの総数を数える方法が見つからないように見えることです。」
備考:質問のタイトルと本文は反対のことを求めています。タイトルでは、GCルートを介して到達できなくなったオブジェクトの数を求めていますが、本文では、「ライブ」オブジェクト、つまり、GCルートを介して到達できるオブジェクトの数を求めています。 。
基本的に.NETのオブジェクトは参照カウントされないため、これを行う方法がない可能性があることから始めましょう。そのため、オブジェクトへの最後の参照が消えたり消えたりしても、すぐに「不要」としてマークすることはできません。スコープの。.NETのマークアンドコンパクトガベージコレクターは、どのオブジェクトが生きていて、実際のガベージコレクション中(「マーク」フェーズ中)に再利用できるかのみを検出すると思います。ただし、この情報は事前に、つまりGCが発生する前に必要なようです。
そうは言っても、ここにおそらくあなたの最良の選択肢があります:
おそらく、.NETのマネージドフレームワーククラスライブラリでの最善の策は、パフォーマンスカウンターです。ただし、適切なカウンターが利用できるようには見えません。さまざまなGC世代で割り当てられたバイト数を示すパフォーマンスカウンターがありますが、ライブ/デッドオブジェクトの数のカウンターはありません。
あなたは可能性も見撮りたいCLRの(つまり、実行時の)管理されていない、COMベースのデバッグAPIを。ICorDebugProcess5
インターフェイスを取得した場合、次のメソッドが役立つ可能性があります。
「プロセスでガベージコレクションされるすべてのオブジェクトの列挙子を取得します。」
参照してくださいこの回答へのSO上で同様の質問を。
これは、ライブオブジェクトではなく、ガベージコレクションされるオブジェクトに関するものであることに注意してください。
「現在列挙可能かどうかなど、ガベージコレクションヒープに関する一般的な情報を提供します。」
管理ヒープが列挙可能であることが判明した場合は、次を使用できます…
「マネージヒープ上のオブジェクトの列挙子を取得します。」
この列挙子によって返されるオブジェクトは、次のタイプです。
「マネージヒープ上のオブジェクトに関する情報を提供します。」
これらの詳細には実際には興味がないかもしれませんが、列挙子によって返されるオブジェクトの数だけに興味があるかもしれません。
(私はこのAPIを自分で使用していません。おそらく、より優れた、より効率的な方法があります。)
2015年9月、MicrosoftはGitHubでclrmd
別名Microsoft.Diagnostics.Runtime
と呼ばれるマネージドライブラリを公開しました。これは、上記のアンマネージデバッグAPIと同じ基盤に基づいています。プロジェクトには、GCヒープ内のオブジェクトの列挙に関するドキュメントが含まれています。
ところで。ベンワトソンによる非常に有益な本「WritingHigh-Performance.NET Code」があります。これには、.NETメモリ割り当てとGCをより効率的にする方法に関する確かなヒントが含まれています。
この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。
侵害の場合は、連絡してください[email protected]
コメントを追加