C#プロジェクトを開始したばかりで、C++ .libとそれに対応するヘッダー(.h)ファイルをインポートしたい。
.libではなく.dllに言及しているさまざまな投稿を読みましたが、これは私を混乱させています。
下の画像は、私が参照している.libファイルと.hファイルを示しています。私がしたことは、それらをプロジェクトにドラッグすることだけです。
誰も私にこれを行う方法のより明確な説明を指摘できますか?見た目ほど難しいことはないと思います。
できることは、C++/CLIラッパーを作成し、使用するライブラリの機能をラッパー経由で公開することです。作成されたラッパーDLLは、C#プロジェクトで簡単に参照できます。もちろん、これはマネージ/アンマネージラッパーを作成するために少しの作業を必要としますが、長期的には成果を上げます。
マネージC++プロジェクトを作成するには、C++プロジェクトテンプレートCLRおよびクラスライブラリの下で選択します。ここで、libにリンクし、ヘッダーファイルを使用します。
次に、新しいクラス(refクラス)を作成し、ライブラリをその中にラップします。例は次のようになります。
LibHeader.h
int foo(...);
このようなラッパークラスを作成します。ヘッダー:
Wrapper.h
public ref class MyWrapper
{
public:
int fooWrapped();
};
実装:
Wrapper.cpp
#include Libheader.h
int MyWrapper::fooWrapped()
{
return foo();
}
簡単にするために、名前空間とすべての適切なものは省略されています。これで、他のマネージクラスと同じくらい簡単に、C#コードでMyWrapperを使用できます。もちろん、libのインターフェースがより複雑になると、もう少し考える必要がありますが、それはlib-codeをアプリケーションから分離するのに役立つかもしれません。それにいくつかの光を当てることを願っています。
その理由は主に、C++
がアンマネージ言語であるという事実によるものです。 C#
は管理言語です。マネージドおよびアンマネージドとは、言語がメモリを管理する方法を指します。
C++
独自のメモリ管理(割り当てと解放)を行う必要があります。C# .NET Framework
は、メモリ管理を ガベージコレクター で行います。あなたはmustnew
を呼び出すすべての場所を確認し、delete
を呼び出す必要があり、malloc
規則を使用している場合はfree
とC
についても同様です。
関数呼び出しの周りにラッパークラスの束を作成し、C++
コードのメモリリークがないことを確認する必要があります。
(私の知る限り)あなたの主な問題は、アンマネージコードをマネージコードに静的にリンクできないため、C#
でこれらの関数を直接呼び出すことができないことです。
すべてのライブラリ関数をC++
でラップするには、.dllを記述する必要があります。実行したら、C#
相互運用機能を使用して、これらの関数をdllから呼び出すことができます。
[DllImport("your_functions.dll", CharSet = CharSet.Auto)]
public extern void your_function();
「見た目ほど難しい」。 C++とC#はあいまいです。 1つ目は決定論的な破壊で、2つ目は破壊的ではありません。ここで、ガベージコレクターによって呼び出されるファイナライザーへの破壊を遅らせるC++/cliを記述します。ガベージコレクターは、スレッド全体で問題を引き起こします(スレッドセーフ、C++メンバー(c ++/cliで使用)は有効ですか?、... )。さらに悪いことに、GCはC++オブジェクトが小さい(ポインター)ことを示唆し、ある種のメモリリークを引き起こす可能性があります(遅いオブジェクトの割り当て解除が遅いため)。基本的に、C++/cli GCの上にGCを記述して、メインスレッドなどの非C++/cli(!)オブジェクトを削除することになります。それはすべて非常識です...