ホームページ >バックエンド開発 >C++ >C# と C DLL 間で文字列を効率的に渡すにはどうすればよいですか?

C# と C DLL 間で文字列を効率的に渡すにはどうすればよいですか?

Patricia Arquette
Patricia Arquetteオリジナル
2025-01-01 01:19:091025ブラウズ

How to Efficiently Pass Strings Between C# and a C   DLL?

C# と C DLL の間で文字列を渡す: 最小限の例

このクエリでは、開発者は C# と C DLL の間で文字列を渡すのに苦労しています。 DLL。彼らのコードを分析すると、彼らの努力を妨げる根本的な問題が明らかになりました。それは、相互運用境界における C std::string と C# 文字列間の非互換性です。

彼らが定義した C DLL 関数:

extern "C" {
    string concat(string a, string b){
        return a + b;
    }
}

C#から直接アクセスすることはできません。これは、std::string が相互運用に適したデータ型ではなく、相互運用の境界を越えて渡すべきではないためです。

この問題を解決するには、開発者は相互運用に適した代替のデータ型を使用する必要があります。一般的なアプローチは、異なるプログラミング言語間で簡単にマーシャリングできる文字のヌル終了配列を利用することです。以下は C コードの修正バージョンです。

extern "C" {
    void concat(char* str1, char* str2, char** result)
    {
        int len1 = strlen(str1);
        int len2 = strlen(str2);
        int resultSize = len1 + len2 + 1; //null-terminator included
        *result = (char*)malloc(resultSize); //allocate memory for the result string
        strcpy(*result, str1);
        strcat(*result, str2); //append str2 to str1
    }
}

この関数は 3 つのパラメータを取ります。2 つの入力文字配列 (str1 と str2) と、割り当てられて返される結果文字配列 (*result) です。 caller.

C# では、次のようにコードを調整できます。

[DllImport("*****.dll", CallingConvention = CallingConvention.Cdecl)]
    static extern void concat(string str1, string str2, StringBuilder result);

...

StringBuilder result = new StringBuilder(10);
concat("a", "b", result);
Console.WriteLine(result.ToString());

このコードは、 10 文字の容量を持つ StringBuilder を作成し、結果パラメータとして C 関数に渡します。関数の実行後、連結された文字列が StringBuilder で使用できるようになります。

このアプローチを利用することで、開発者は相互運用互換のデータ型を使用して文字列が受け渡され、以前に発生した System.AccessViolationException を解決することを保証します。 .

以上がC# と C DLL 間で文字列を効率的に渡すにはどうすればよいですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。