2009-07-01 9 views
1

私はそのようなコードを持っている:他のオブジェクトが指し示されている場合は、本当にメモリを解放できますか?

public class A: IDisposable 
    { 
     public CPlusCode cPlusCode{get;set;} 

    public void CallB() 
    { 
     using(bCode = new B(cPlusCode)) 
     { 
       //do everything in B 
     } 
    } 

    public void Dispose() 
    { 
     cPlusCode.Dispose(); 
    } 
    } 

    public class B: IDisposable 
    { 
    private CPlusCode cpp; 
     public B(CPlusCode cPlus) 
    { 
    cpp= cPlus; 
    } 
    public void Dispose() 
    { 
    cpp.Dispose(); 
    //dispose everything 
    } 
    } 

    public static void Main() 
    { 
      for(int i=0; i<100000; i++) 
       { 
         var aObject = new A(); 
        aObject .CallB(); 
       } 
    } 

の問題は、私がMainを実行し、Bはインスタンス化するために多くのメモリを食べる、と私の観察から、プログラムによって食べられたメモリではないと思われるとき解放。

他のオブジェクトが指し示されている場合は、本当にメモリを解放できますか?

+0

リソースのコピーを作成したり、新しいリソースを割り当てたりしない限り、リソースをBに破棄しないでください。 CallB()を同じオブジェクトで2回呼び出すと、コードが書き込まれる方法で例外が発生します。 –

答えて

2

GCは必要と判断したときに実行されるため、「タイムリー」は関係ありません。それが起こると起こります。つまり、非決定論的です。

6

IDisposableは、管理対象メモリの再生とは関係ありません。 IDisposableは、ハンドルなどのガベージコレクションで処理されないリソースを型から解放することができます。通常の.NET型では、オブジェクトが参照されなくなったときにガベージコレクタがメモリを再利用します。

+0

申し訳ありません私はそれを明確にするために質問を編集します。 – Graviton

0

私の所見では、プログラムによって食べたメモリが ではないと思われます。

これは完全に正常です。プログラムは一定量の未使用メモリにハングアップし、システムが実際にそれを必要とする場合に解放されます。

パフォーマンスのための最良のものは、メモリ使用率をできるだけ小さく保つことだと思うかもしれませんが、実際には逆です。コンピュータは、未使用のメモリが大量であることから何の利点もありません。そのため、最高のパフォーマンスを得るには、アプリケーションが実際に必要になるまでメモリ使用量を最小限に抑えるために余分な作業を行うべきではありません。

にそれを指して、他のオブジェクトがある場合 メモリを本当に自由に処分することはできますか?

はいなし...

ものはDisposeメソッドによって解除することができ、オブジェクトは他のオブジェクトが含まれている場合しかし、オブジェクト自体を解放しませんオブジェクト上のDisposeを呼び出します。それだけでメモリが解放されるわけではありませんが、ガベージコレクタは次の実行時にそれを実行します。

2

Disposeは単なる方法です。何もする必要はありません。

オブジェクトに対してDisposeを呼び出した後、オブジェクトはまだ存在しますが、安全に使用できなくなります。ただし、ランタイムはこれを強制するのに役立たない。 Dispose(「バグの捕捉に役立つように設計された」)の固体実装は、オブジェクト内の_disposedフラグをtrueに設定し、オブジェクト上の他のすべてのメソッドは、そのフラグがtrueの場合はObjectDisposedExceptionをスローします。Disposeメソッド自体は、さらなる呼び出し)。しかし、このパターンを実施するにはどのくらいの距離を置くのかは、実装者にとってまったく問題です。

例はFileStreamです。開いているファイルがある場合、プロセスのハンドル数は1増加します。Disposeを呼び出すと、ハンドル数が減少します。しかし、これは、著者がDisposeの方法を書いたためです。

これは次の問題につながります。タスクマネージャでプロセスのハンドルカウントがわかりますが、これは非常に簡単なカウンタですが、メモリ使用量をどのように測定していますか?タスクマネージャに表示される数値は単純な数値ではありません。

+1

私はむしろObjectDisposedExceptionをスローしたいが、残りは完全に同意する。 http://msdn.microsoft.com/en-us/library/system.objectdisposedexception.aspx –

+0

良いことに、特定の例外があることはわかりませんでした。答えを更新する。 –

0

Dispose()内のすべての管理されていないリソースを解放している場合、そのオブジェクトへのすべての参照を解放した後、そのオブジェクトを収集する必要があります。

ただし、Aというオブジェクトをご使用の例に廃棄することはありません。IDisposableです。 ABの参照が含まれていて、Aを処分しないと、AAへの参照を作成している管理されていないものがある場合は、Bのコレクションが遅れることがあります。

例では、アンマネージコードがAによって参照されているようですので、Aはそれを廃棄する責任があります。

関連する問題