2011-11-08 6 views
4

私はCOMタイプ(tlbimp.exeを使用して作成)とこのオブジェクトをラップするC#クラスを持っています。私はC#ラッパーのファイナライザでいくつかのクリーンアップを実行したいです。私はしかし、私の知る限ります。tlbimpを伝えることができるよう、ファイナライザは、任意の順序で実行することができますので、私はファイナライザを実装する任意のオブジェクトを使用しようとするべきではないことを知っているファイナライザでCOMオブジェクトを参照/使用できますか?

public class MyClass : IDisposable 
{ 
    private IMyComObject comObject; 

    public MyClass() 
    { 
     comObject = new MyComObject(); 
    } 

    public void Dispose() 
    { 
     Dispose(true); 
     GC.SuppressFinalize(this); 
    } 

    ~MyClass() 
    { 
     Dispose(false); 
    } 

    protected virtual void Dispose(bool disposing) 
    { 
     // Be tollerant of partially constructed instances 
     if (comObject != null) 
     { 
      comObject.Cleanup(); 
      // Account for object being disposed twice 
      comObject = null; 
     } 
    } 

    // Other bits go here... 
} 

:ガイドラインhere以下の私はこのような何かを書くかもしれません生成されたCOMタイプはファイナライザを実装していないため、上記はOKです。

これについての公式の文書は見つかりませんでしたので、私の質問はです。ファイナライザでCOMオブジェクトを参照して使用するのは安全ですか?

+0

あなたのDisposeメソッドの先頭にGCを起動しようとしましたか? – Bond

+0

ファイナライザを実装しているので、COMオブジェクトが解放されます。だから、それは安全ではありません。 –

+0

@HansPassant私はそれを考えていましたが、これを述べている文書を見つけることができず、逆アセンブリのファイナライザも表示されません。 – Justin

答えて

-1

抽象COMラッパークラスを作成しました。そこから、すべてのCOMラッパークラスを派生させました。私はとてもうまく動作します。遅いバインディングが必要なので、元のコードはVBです。私のアプリの残りはC#で書かれています。

public abstract class ComWrapper : IDisposable 
{ 
    protected internal object _comObject; 
    protected ComWrapper(object comObject) 
    { 
     _comObject = comObject; 
    } 

    #region " IDisposable Support " 

    private bool _disposed = false; 

    protected virtual void FreeManagedObjects() 
    { 
    } 

    protected virtual void FreeUnmanagedObjects() 
    { 
     ReleaseComObject(_comObject); 
    } 

    private void Dispose(bool disposing) 
    { 
     if (!_disposed) { 
      if (disposing) { 
       FreeManagedObjects(); 
      } 
      FreeUnmanagedObjects(); 
      _disposed = true; 
     } 
    } 

    public void Dispose() 
    { 
     Dispose(true); 
     GC.SuppressFinalize(this); 
    } 

    protected override void Finalize() 
    { 
     Dispose(false); 
     base.Finalize(); 
    } 

    #endregion 
} 

public static class Helpers 
{ 
    public static void ReleaseComObject(ref object o) 
    { 
     if ((o != null)) { 
      try { 
       Marshal.ReleaseComObject(o); 
      } catch { 
      } finally { 
       o = null; 
      } 
     } 
    } 

    public static string ToDotNetString(object comString) 
    { 
     if (comString == null) { 
      return string.Empty; 
     } 
     string s = comString.ToString(); 
     ReleaseComObject(ref comString); 
     return s; 
    } 
} 
+0

これは実際に私の質問に答えない(またはコンパイルする) – Justin

関連する問題