如何将3D元素传递到JNI?



我正在做一个项目,需要在c++中做一些3D数组的计算。我需要将这个3D数组从Java传递到c++,做一些计算,然后返回它。我正在使用JNI,我很新的,所以我不知道很多。我正试图使一个样本程序来测试这一点,并使用它作为参考。我已经得到了一个2D数组传递到c++,但无法找出3D部分。我使用这个解决方案构建了2D部分。

这是我现在的c++代码(这适用于2D数组):

float** testFunction(float **a)
{
printf("Hello from JNI!n");
printf("Point at %d,%d is: %fn", 1, 2, a[1][2]);
return a[1][2];
}
jfloat JNICALL Java_JNIArray_integrateWithTrapezoid(JNIEnv *env, jobject thisObj, jobjectArray jarr)
{
int sizex = env->GetArrayLength(jarr);
jfloatArray dim = (jfloatArray)env->GetObjectArrayElement(jarr, 0);
int sizey = env->GetArrayLength(dim);
float **localArray;
localArray = new float *[sizex];
for (int i = 0; i < sizex; i++)
{
jfloatArray oneDim = (jfloatArray)env->GetObjectArrayElement(jarr, i);
jfloat *element = env->GetFloatArrayElements(oneDim, 0);
localArray[i] = new float[sizey];
for (int j = 0; j < sizey; j++)
{
localArray[i][j] = element[j];
}
}
return testFunction(localArray);
}

任何帮助都太好了。这件事我完全不知情。如果我忘了提供任何需要的信息,请告诉我。

谢谢。编辑:

感谢@Botje,这是有效的:

void trapezoidalintegral(float ***a)
{
printf("Hello from JNI!n");
printf("Point at %d, %d, %d is: %fn", 1, 2, 2, a[1][2][2]);
return;
}
float *thirdLevel(JNIEnv *env, jfloatArray arr)
{
jsize len = env->GetArrayLength(arr);
float *ret = new float[len];
env->GetFloatArrayRegion(arr, 0, len, ret);
return ret;
}
float **secondLevel(JNIEnv *env, jobjectArray arr)
{
jsize len = env->GetArrayLength(arr);
float **ret = new float *[len];
for (int i = 0; i < len; i++)
{
jobject item = env->GetObjectArrayElement(arr, i);
ret[i] = thirdLevel(env, (jfloatArray)item);
env->DeleteLocalRef(item);
}
return ret;
}
float ***firstLevel(JNIEnv *env, jobjectArray arr)
{
jsize len = env->GetArrayLength(arr);
float ***ret = new float **[len];
for (int i = 0; i < len; i++)
{
jobject item = env->GetObjectArrayElement(arr, i);
ret[i] = secondLevel(env, (jobjectArray)item);
env->DeleteLocalRef(item);
}
return ret;
}
JNIEXPORT jobjectArray JNICALL Java_JNIArray_integrateWithTrapezoid(JNIEnv *env, jobject thisObj, jobjectArray jarr)
{
float ***returningArray;
returningArray = firstLevel(env, jarr);
trapezoidalintegral(returningArray);
jclass *pClass;
jclass cls1;
jclass jcls1;
jclass jcls2;
jobject obj2;
cls1 = env->GetObjectClass(thisObj);
// jfieldID fid1 = env->GetFieldID(cls1, "ptr", "J");
// pClass = (jclass *)env->GetLongField(thisObj, fid1);
jcls1 = env->FindClass("[[F");
jcls2 = env->FindClass("[F");
jobjectArray array1 = env->NewObjectArray(3, jcls1, NULL);
for (int i = 0; i < 3; i++)
{
jobjectArray array2 = env->NewObjectArray(3, jcls2, NULL);
for (int j = 0; j < 3; j++)
{
jfloatArray array3 = env->NewFloatArray(3);
env->SetFloatArrayRegion(array3, 0, 3, returningArray[i][j]);
env->SetObjectArrayElement(array2, j, array3);
}
env->SetObjectArrayElement(array1, i, array2);
}
env->DeleteLocalRef(cls1);
env->DeleteLocalRef(jcls1);
env->DeleteLocalRef(jcls2);
return array1;
}

就像你的数据一样构造你的程序:

float* thirdLevel(JNIEnv *env, jfloatArray arr) {
jsize len = env->GetArrayLength(arr);
float* ret = new float[len];
env->GetFloatArrayRegion(arr, 0, len, ret);
return ret;
}
float** secondLevel(JNIEnv *env, jobjectArray arr) {
jsize len = env->GetArrayLength(arr);
float** ret = new float*[len];
for (int i = 0; i < len; i++) {
jobject item = env->GetObjectArrayElement(arr, i);
ret[i] = thirdLevel(env, (jfloatArray)item);
env->DeleteLocalRef(item);
}
return ret;
}
float*** firstLevel(JNIEnv *env, jobjectArray arr) {
jsize len = env->GetArrayLength(arr);
float*** ret = new float**[len];
for (int i = 0; i < len; i++) {
jobject item = env->GetObjectArrayElement(arr, i);
ret[i] = secondLevel(env, (jobjectArray)item);
env->DeleteLocalRef(item);
}
return ret;
}

最新更新