Aufruf der C ++ - Funktion aus C # mit vielen komplizierten Eingabe- und Ausgabeparametern

Ich bin neu in C #, habe aber intensiv mit C ++ gearbeitet. Ich habe eine C ++ - Funktion, die von C # aufgerufen werden muss. Nachdem ich einige Antworten von SO und ein wenig Google gelesen habe, komme ich zu dem Schluss, dass ich eine reine C-Schnittstelle für die Funktion erstellen muss. Ich habe das getan, bin aber immer noch verwirrt darüber, wie ich es von C # aus aufrufen soll.

Die Funktion in C ++ sieht folgendermaßen aus:

int processImages(
    std::string& inputFilePath,                      // An input file
    const std::vector<std::string>& inputListOfDirs, // Input list of dirs
    std::vector<InternalStruct>& vecInternalStruct,  // Input/Output struct
    std::vector<std::vector< int > >& OutputIntsForEachFile,
    std::vector< std::vector<SmallStruct> >& vecVecSmallStruct, // Output
    int verboseLevel
    );

Dieselbe in C konvertierte Funktion sieht folgendermaßen aus:

int processImagesC(
    char* p_inputFilePath,               // An input file
    char** p_inputListOfDirs,            // Input list of dirs
    size_t* p_numInputDirs,              // Indicating number of elements
    InternalStruct* p_vecInternalStruct, // Input/Output struct
    size_t* p_numInternalStructs, 
    int** p_OutputIntsForEachFile,       // a 2d array each row ending with -1
    size_t* p_numOutputIntsForEachFile //one number indicating its number of rows
    SmallStruct** p_vecVecSmallStruct,   // Output
    size_t* p_numInVecSmallStruct,
    int verboseLevel
    );

Dies basiert aufdiese Rat.

Jetzt muss ich das von C # aus aufrufen, wo die Verwirrung ist. Ich habe mein Bestes versucht, um die Strukturen zu konvertieren.

Der C # -Code sieht folgendermaßen aus:

[DllImport(
    @"C:\path\to\cppdll.dll", CallingConvention=CallingConvention.Cdecl, 
    EntryPoint="processImagesC", SetLastError=true)]
[return: MarshalAs(UnmanagedType.I4)]
unsafe public static extern int processImagesC(
    String inputFilePath,
    String[] inputListOfDirs,
    ref uint numInputListOfDirs,

    // Should I use ref InternalStruct * vecInternalStruct?
    ref InternalStruct[] vecInternalStruct, 

    ref uint numInternalStruct,

    // Or ref int[] or ref int[][] or int[][]?
    ref int[][] OutputIntsForEachFile, 

    ref uint numOutputIntsForEachFile,

    // again, ref ..[], [][], or ref [][]?
    ref SmallStruct[][] vecVecSmallStruct, 

    int verboseLevel
);

Es gibt Speicherzuordnungen für alle Ausgabevariablen (Zeiger), die im C / C ++ - Code ausgeführt werden. Dies bedeutet wahrscheinlich, dass wir den Code als unsicher und korrekt deklarieren müssen.

Wie gehen wir mit der Speicherfreigabe um? Soll ich eine andere API (Funktion) schreiben, die die Freigabe von Objekten / Arrays übernimmt, die von C / C ++ zugewiesen wurden?

Der C ++ - Code muss standardkonform und plattformunabhängig sein, daher kann ich keine windowsspezifischen Elemente einfügen.

Ich hoffe, jemand könnte dies verstehen und eine Antwort geben oder mich zumindest in die richtige Richtung weisen.

Antworten auf die Frage(4)

Ihre Antwort auf die Frage