Visual Studio を使用した Windows 上での C# コードとアンマネージド C++ コードの混合

StackOverflow https://stackoverflow.com/questions/76629

質問

C# コードからアンマネージ C++ ライブラリを呼び出したいと考えています。潜在的な落とし穴と取るべき予防策は何ですか?お時間をいただきありがとうございます。

役に立ちましたか?

解決

この質問は範囲が広すぎます。唯一の合理的な答えは P/Invoke ですが、これは Windows 用にプログラミングしたい場合は Win32 API を知る必要があると言っているようなものです。

ほぼすべての本が P/Invoke について書かれています (http://www.amazon.com/NET-COM-Complete-Interoperability-Guide/dp/067232170X)、そしてもちろんウェブサイト全体が作成されました: http://www.pinvoke.net/.

他のヒント

これにはいくつかの方法があります。1 つは、アンマネージ C++ ライブラリを更新してマネージド C++ 拡張機能ラッパーを配置し、C# でこれらのクラスを直接利用できるようにすることです。これには少し時間がかかりますが、従来のアンマネージ コードへの優れた橋渡しとなります。ただし、マネージド C++ 拡張機能は、構文がアンマネージド C++ に似ていますが、十分に訓練された目であれば違いがわかる程度に近いため、それ自体をナビゲートするのが少し難しい場合があることに注意してください。

もう 1 つの方法は、マネージド C++ で COM クラスを実装し、自動生成された相互運用アセンブリを介して C# でそれを利用することです。COM の使い方を十分に知っている場合は、この方法の方が簡単です。

お役に立てれば。

P/Invoke について説明しています。つまり、C++ ライブラリは DLL インターフェイスを介してそれ自体を公開する必要があり、そのインターフェイスは呼び出し属性を介して P/Invoke に記述できるほど単純である必要があります。マネージ コードがアンマネージ世界を呼び出す場合、パラメーターをマーシャリングする必要があるため、パフォーマンスにわずかな影響が出る可能性があるように見えますが、マーシャリングが重要かどうかを確認するには、いくつかのテストを行う必要があります。

まず最も簡単な方法は、すべての C++ 機能が「C」スタイルの関数として公開されていることを確認することです。必ず関数を _stdcall として宣言してください。

extern "C" __declspec(dllexport) int _stdcall Foo(int a)

特にポインターや wchar_t * などのマーシャリングが正しく行われていることを確認してください。間違えるとデバッグが難しくなる可能性があります。

どちらかの側からデバッグしますが、両方からデバッグすることはできません。ネイティブとマネージドを混合してデバッグすると、デバッガーが非常に遅くなる可能性があります。一度に 1 面ずつデバッグすると、時間を大幅に節約できます。

より具体的にするには、より具体的な質問が必要になります。

P/Invoke を介してアンマネージ コードを呼び出すこともできます。コードで現在 COM を使用していない場合、これは簡単な場合があります。この方法を採用する場合、おそらく「C」バインディングを使用してコード内に特定のエクスポート ポイントをいくつか記述する必要があると思います。

私の経験上、おそらく最も注意しなければならないのは、決定論的なガベージ コレクションがないため、以前は実行されると思われていたときにデストラクターが実行されなくなることです。この点に留意し、IDisposable またはその他のメソッドを使用して、マネージド コードが必要なときにクリーンアップされるようにする必要があります。

もちろん、コードを外部エントリポイントを備えた DLL としてパッケージ化した場合には、常に PInvoke も存在します。どの選択肢も痛みを伴わないものではありません。これらは、a) COM またはマネージド C ラッパーの作成スキル、b) PInvoke での腕の良さのいずれかに依存します。

見てみましょう しゃがむ, 、私たちはこれをプロジェクトに良い影響を与えるために使用し、C++ API を他の言語プラットフォームに公開します。

これは、C++ ライブラリの周囲に薄いラッパーを効果的に構築する、よく管理されたプロジェクトです。これにより、C# などの言語がネイティブ コードと直接通信できるようになり、グルー コードを実装 (およびデバッグ) する手間が省けます。

優れた PInvoke の例が必要な場合は、以下を参照してください。 PInvoke.net. 。ほとんどの Win API 関数を呼び出す方法の例が含まれています。

この記事のツールも使用できます インサイドアウトをクリア:PInvoke これにより、.h ファイルが C# ラッパーに変換されます。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top