JNI基础(5): JNI中引用类型
2022-01-11 本文已影响0人
MemetGhini
JNI中数据类型分为两种,一种是基础数据类型,另一种是引用类型。在调用Java native方法将实参传递给C/C++函数的时候,会自动将java形参的数据类型自动转换成C/C++相应的数据类型,所以我们在写JNI程序的时候,必须要明白它们之间数据类型的对应关系。下面先介绍引用类型。
引用类型包括:类,实例,数组。引用类型的映射参见下表:
Java类型 | JNI类型 | 描述 |
---|---|---|
Object | jobject | 任何Java对象,或者没有对应java类型的对象 |
Class | jclass | Class类对象 |
String | jstring | 字符串对象 |
Object[] | jobjectArray | 任何对象的数组 |
boolean[] | jbooleanArray | 布尔型数组 |
byte[] | jbyteArray | 比特型数组 |
char[] | jcharArray | 字符型数组 |
short[] | jshortArray | 短整型数组 |
int[] | jintArray | 整型数组 |
long[] | jlongArray | 长整型数组 |
float[] | jfloatArray | 浮点型数组 |
double[] | jdoubleArray | 双浮点型数组 |
特殊类型: void | void | 没有返回值 |
- 引用类型不能直接使用,需要通过jni函数转换后才能使用。
- java中所有的对象在jni中统一都是jobject
- java中的所有的class在jni中统一都是jclass
- java中的stringjni中统一都是jclass
- java中的string[] 在jni中是jobjectArray
- 其它基本类型都有对应的jxxxArray类型,所有array类型的操作方法基本一致,都继承自jarray。
java String数组中获取最后一个元素:
//先获取数组长度
int len = env->GetArrayLength(str_arry);
//获取某个元素
jstring str1 = (jstring)env->GetObjectArrayElement(str_arry, len - 1);
const char* c_str = env->GetStringUTFChars(str1, 0);
jstring ret = env->NewStringUTF(c_str);
env->ReleaseStringUTFChars(str1, c_str);
return ret;
Java Int数组常用操作:
//截取某两个元素
int buf[2];
env->GetIntArrayRegion(int_array, 0, 2, buf);
LOGI("两个元素: %d , %d", buf[0], buf[1]);
//获取c数组指针
jboolean isCopy;
int* intArr = env->GetIntArrayElements(int_array, &isCopy);
LOGI("是否为拷贝:%s", isCopy ? "是" : "否");
//更改数据
int len = env->GetArrayLength(int_array);
intArr[len-1] = 99;
env->ReleaseIntArrayElements(int_array, intArr, JNI_ABORT);//关注第三个参数
//返回自定义的数组
jintArray jintArray1 = env->NewIntArray(2);
env->SetIntArrayRegion(jintArray1, 0, 2, buf);
return jintArray1;
- ReleaseIntArrayElements第三个参数:
- 0:刷新java数组,释放c/c++数组
- 1 = JNI_COMMIT: 只刷新java数组
- 2 = JNI_ABORT: 只释放c/c++数组 free buffer without copying back
- 如果设置 0 和 1 , 那么 如果修改了 int 数组的值 , 那么最终 Java 层的值会被修改
- 如果设置 2 , 那么 如果修改了 int 数组的值 , 那么最终 Java 层的值不会被修改