5
MyObject obj = new MyObject();

「new」キーワードがコンストラクターを呼び出し、マネージド ヒープでオブジェクトを初期化することはわかっています。

私の質問は、CLRが以下をどのように行っているかです。

  1. 上記の行は CLR によってどのように実行されますか?
  2. CLRによってオブジェクトにメモリがどのように割り当てられますか?
  3. CLR はオブジェクトのサイズをどのように決定しますか?
  4. ヒープからオブジェクトにメモリを割り当てるスペースがない場合、CLR はどのようにそれを知るのでしょうか?
4

1 に答える 1

2

参照型 (クラス、デリゲート、インターフェイス、文字列、またはオブジェクト) が作成されると、ヒープに割り当てられます。Net には、(gen0、gen1、gen2) (スモール オブジェクト ヒープ) と LOH (ラージ オブジェクト) の 4 つの異なるヒープがあります。ヒープ)。85k 以下のものはすべて、作成時間 (gen0 から gen1、gen2 に移動など) に応じて、最初の 3 つのヒープのいずれかに移動します。85k を超えるオブジェクトは LOH に配置されます。LOH は決して圧縮されないため、最終的に、私が行っているタイプの割り当ては、オブジェクトがそのメモリ空間に散在するため、最終的に OOM エラーを引き起こします。これらはマネージド ヒープと呼ばれます。

オブジェクトを作成するには、 new キーワードを使用するだけです。.NET は、オブジェクトの作成、初期化、正しいヒープへの配置、および必要な余分なメモリの予約を処理します。その後は、使い終わったときにオブジェクトを削除する必要がないため、そのオブジェクトのことをほとんど忘れることができます。

new キーワードを使用して参照型オブジェクトを作成すると、それはヒープに配置され、その参照は現在実行中のスタックで主に使用されます。オブジェクトを参照として使用できる可能性のあるソースは他にもあります。

  1. グローバル/静的オブジェクト参照
  2. CPU レジスタ
  3. オブジェクトのファイナライズの参照 (詳細は後述)
  4. 相互運用参照 (COM/API 呼び出しに渡される .NET オブジェクト)
  5. スタック参照 (主にここで使用)

これら 5 つは、実際にはオブジェクト参照階層が形成される GC ルート ノードです。通常、Order クラスを格納するコレクションを持つ、従来の Customer クラスを想像してみてください。Order が注文コレクションに追加されると、コレクション自体が追加された注文への参照を保持します。Customer クラスのインスタンスにもそれへのスタック参照があった場合。

これは、複雑なオブジェクトの階層がどのように形成されるか、GC が参照をどのように認識するかです。

例えば。Customer オブジェクトのスタック参照 -> 注文の List オブジェクトへの参照 -> 個々の注文の参照。

これらの 5 つのルートからの参照を失うものはすべて、GC になりがちです。

オブジェクトにメモリを割り当てる方法は少し複雑で、指定された MKK のように通常は時間とともに増加しますhttp://msdn.microsoft.com/en-us/magazine/cc163791.aspx

簡単な例は次のとおりです。

class MyClass 
{ 
    string Test="Hello world Wazzup!"; 
    byte[] data=new byte[86000];  
}

割り当てられたときの MyClass のサイズには次のものが含まれると簡単に推測できます。

• 19 文字

• 86,000 バイト。

実際、オブジェクトのサイズには、一般的なクラスのものと、文字列へのオブジェクト ポインターとバイト配列 (クラス レベル変数) を格納するために必要なメモリのみが含まれ、これらはヒープに個別に割り当てられます。文字列は SO​​H に割り当てられ、そのオブジェクト参照はクラスのインスタンスによって保持されます。バイト配列は 85 KB より大きいため、LOH に割り当てられます。

SOH は圧縮でき、断片化はありませんが、LOH はメモリ内で断片化することができます。

よろしく。

于 2012-06-14T06:07:05.453 に答える