Unity, c ++ собственный плагин, не соответствующий байтовому массиву - PullRequest
0 голосов
/ 26 апреля 2018

В моем родном плагине C ++ у меня есть вызов

vector<unsigned char> getCPPOutput() {
    return some_vector;
}

На моей стороне C # у меня есть звонок

[DllImport("MySharedObj")]
static extern byte[] getCPPOutput();

По некоторым причинам, хотя у меня есть несоответствие между этими двумя вызовами, а именно, если в моем C ++ я проверяю размер массива, который я получаю как вывод: 16777216 (для моего конкретного случая).

Когда я проверяю размер байтового массива, я получаю: 170409961

Вызов на C # действительно прост, это что-то вроде:

byte[] outputBuffer = getCPPOutput();

Там нет никакого предварительного распределения вообще. Есть ли что-то, что мне нужно перед вызовом функции?

Я вообще не эксперт по C #, возможно, я упускаю что-то очень глупое.

1 Ответ

0 голосов
/ 26 апреля 2018

Ваш тип возврата - byte[] в C #, но vector<unsigned char> в C ++. Они не совпадают. В других ваших вопросах вам предлагалось заполнить массив, а не возвращать его, но вы все равно хотите вернуть массив, вот как это сделать:

Преобразовать Vector в массив и вернуть его. Тип возврата C ++ должен быть char*, а тип возврата C # должен быть IntPtr. Кроме того, вам нужен способ сообщить C # размер массива. Вы можете сделать это с аргументом. На стороне C # вы должны снова создать новый массив с размером, возвращаемым этим аргументом. После этого используйте Marshal.Copy, чтобы скопировать данные из IntPtr в этот новый массив.

C ++:

char* getCPPOutput(int* outValue)
{
    //Convert the Vector to array
    char* vArrray = &some_vector[0];
    *outValue = some_vector.size();
    return vArrray;
}

C #:

[DllImport("MySharedObj", CallingConvention = CallingConvention.Cdecl)]
public static extern IntPtr getCPPOutput(out int outValue);


//Test
void Start() 
{
 int size = 0;

 //Call and return the pointer
 IntPtr returnedPtr = getCPPOutput(out size);

 //Create new Variable to Store the result
 byte[] returnedResult = new byte[size];

 //Copy from result pointer to the C# variable
 Marshal.Copy(returnedPtr, returnedResult, 0, size);


 //The returned value is saved in the returnedResult variable

}

Примечание о вашем коде C ++:

Я не видел объявление вашей some_vector переменной. Если это объявлено в этой функции как локальная переменная, то это в стеке, и вам нужно динамически выделить новый массив с ключевым словом new и создать другую функцию, чтобы освободить его с ключевым словом delete после получения его на C # боковая сторона. Вы не можете вернуть массив в стеке, если он не объявлен как объект static или не выделен динамически с ключевым словом new.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...