2011-01-18 12 views
2

私はネイティブなC++のdll、いくつかのヘッダファイルとインポートライブラリを持っています。 dllで定義されているC#内でオブジェクトをインスタンス化する方法はありますか?私はあなたのオプションが唯一だと思いC#からアンマネージC++クラスをインポートして使用する方法は?

  1. DLLIMPORTおよび外部C関数
+0

C++コードはboostのような他のライブラリに依存しますか? –

+0

はい。 FLOPC++(しかし、私のC++コードではありません)。 –

答えて

7

C++/CLIはこれにはあなたの友人です。ただし、標準のC++オブジェクトをC++/CLIのrefクラスまたはvalueクラス(.NETの場合)に格納することはできません。 C++/CLIクラス内Handle<MyCppClass>^ handle;

#pragma once 
#include <boost/shared_ptr.hpp> 

template <typename T> 
ref class Handle 
{ 
    boost::shared_ptr<T>* t; 

    !Handle() 
    { 
     if (t != nullptr) 
     { 
      delete t; 
      t = nullptr; 
     } 
    } 

    ~Handle() { this->!Handle(); } 

public: 
    Handle() : t(new boost::shared_ptr<T>((T*)0)) {} 

    Handle% operator=(T* p) 
    { 
     if (p != t->get()) t->reset(p); 
     return *this; 
    } 

    static T* operator&(Handle% h) { return h.t->get(); } 
    static boost::shared_ptr<T> operator->(Handle% h) { return *h.t; } 

    T& reference() { return *t->get(); } 
    T const& const_reference() { return *t->get(); } 
}; 

使用法:だから、私は、生産コードで使用以下のクラス(あなたが変更できる)に頼る必要があります。その後、スタブメソッドを実装し、handleメンバに転送します。ガベージコレクションされたオブジェクトは、それ以上ポインタがない場合、C++クラスインスタンスのデストラクタを呼び出します。

public ref class Foo 
{ 
    void bar() { handle->bar(); } 

internal: 
    Handle<CppNamespace::Foo>^ handle; 
}; 
+0

これは一般的なラッパーです。 C++/CLIで。メモリ操作を管理します。 C#からネイティブC++にアクセスしたい場合は、自分のC++/CLIコード(このクラスを含む)にアクセスしてください。このコードは、ネイティブC++にアクセスします。これは正しいです? –

+0

はいそうです。これは、.NETリソースの非決定論的セマンティクスとC++デストラクタの決定論的性質との間に橋渡しをします。反対の場合(ネイティブC++クラスの.NET型)、 'cli :: gcroot'クラステンプレートを使用します。また、 'cli :: pin_ptr'クラステンプレートで文書化したいかもしれません。 –

3

を使用するCOM

  • にC++のコードをラップする:

    私の知る2つの方法がありますC++/CLIクラスラッパーをビルドします(AC#クラスのように参照することができます)。そうしないと、C#コードからC++クラス(アンマネージド)をインスタンス化できません。

    代わりに、 "醜い"方法かもしれません:ac関数を通してC++クラスをインスタンス化しますが、あなたはC#コードの中のvoidポインタとして扱いますので、基本的に何もしませんこのクラスと対話するための他の機能を作成し、唯一のC関数を)あなたはそれはあなたがC++/CLI

    PSを使用する必要がC++を理解させるかどう

    C#は、Cを理解 C#はC++クラスの基本的な知識を持っていますが、クラスデータ(バイト:フィールドを意味します)をC#で使用できるデータ(属性はいくつかあります)に変換するだけですが、私の提案は完全に避けてください)。

  • +1

    これはオプションですが、彼の唯一の選択肢ではありません。 COMルートは、実装するのが簡単かもしれません(または少なくとももっと簡単に)。 C#は、Interopレイヤを使用してCOMオブジェクトに簡単にアクセスできます。 –

    +0

    実際、私はCOMオプション(および静的なC関数呼び出し)が簡単だと思います。特に:1.あなたがC++/CLIの前に(私のような)前に作業したことがないならば。2. dllのautorが私のものではなく私を実装しなければならないからです。 –

    関連する問題