注册 登录  
 加关注
   显示下一条  |  关闭
温馨提示!由于新浪微博认证机制调整,您的新浪微博帐号绑定已过期,请重新绑定!立即重新绑定新浪微博》  |  关闭

民主与科学

独立之人格,自由之思想

 
 
 

日志

 
 

JNI中参数的传递与操作(中)  

2011-06-07 13:22:58|  分类: 开发专题 |  标签: |举报 |字号 订阅

  下载LOFTER 我的照片书  |
三、数组
JNI提供了对Java数组进行操作的功能。
它提供了两类函数:一类用于操作java的简单型数组,另一类用于是操作对象类型数组的。
简单数组
因为速度的原因,先通过GetXXXArrayElements函数把简单类型的数组转化成本地类型的数组,并返回其数组的指针,然后通过该指针来对拷贝数组进行处理。
对拷贝数组处理完后,通过ReleaseXXXArrayElements函数把修改后的拷贝数组的反射到java数组,
然后释放所有相关的资源。
注意:GetXXXArrayElements函数(见表B)中,XXX代表了数组的类型。这种函数把Java数组看成参数,返回一个指向对应的本地类型的数组的指针
表B

函数

Java数组本地C/C++类型

Java本地C/C++类型

GetBooleanArrayElements

jbooleanArray

Jboolean

GetByteArrayElements

jbyteArray

Jbyte

GetCharArrayElements

jcharArray

Jchar

GetShortArrayElements

jshortArray

Jshort

GetIntArrayElements

jintArray

Jint

GetLongArrayElements

jlongArray

Jlong

GetFloatArrayElements

jfloatArray

Jfloat

GetDoubleArrayElements

jdoubleArray

Jdouble

GetXXXArrayElements系列函数如下
  jboolean * GetBooleanArrayElements (jbooleanArray val0, jboolean * val1)
  jbyte * GetByteArrayElements (jbyteArray val0, jboolean * val1)
  jchar * GetCharArrayElements (jcharArray val0, jboolean * val1)
  jshort * GetShortArrayElements (jshortArray val0, jboolean * val1)
  jint * GetIntArrayElements (jintArray val0, jboolean * val1)
  jlong * GetLongArrayElements (jlongArray val0, jboolean * val1)
  jfloat * GetFloatArrayElements (jfloatArray val0, jboolean * val1)
  jdouble * GetDoubleArrayElements (jdoubleArray val0, jboolean * val1)
第一个参数,val0是你要操作的数组。
第二参数,val1什么意思呢?不知道。一般用0就可以。
ReleaseXXXAarryElements系列函数如下
  void ReleaseBooleanArrayElements (jbooleanArray val0, jboolean * val1, jint val2)
  void ReleaseByteArrayElements (jbyteArray val0, jbyte * val1, jint val2)
  void ReleaseCharArrayElements (jcharArray val0, jchar * val1, jint val2)
  void ReleaseShortArrayElements (jshortArray val0, jshort * val1, jint val2)
  void ReleaseIntArrayElements (jintArray val0, jint * val1, jint val2)
  void ReleaseLongArrayElements (jlongArray val0, jlong * val1, jint val2)
  void ReleaseFloatArrayElements (jfloatArray val0, jfloat * val1, jint val2)
  void ReleaseDoubleArrayElements (jdoubleArray val0, jdouble * val1, jint val2)
参数意义
把数组val0从第0个开始的val2个元素设置为val1地址开始的val2个元素的值
如果想返回一个新的数组,可以先用NewXXXArray函数创建一个Java数组本地C/C++类型数组,然后通过
ReleaseXXXAarryElements/SetXXXArrayRegion函数设置数组值,最后返回直接返回该数组就可以了。
另外我们还可以用GetXXXArrayRegion函数取得数组某段的数据。这来的XXX表示是什么类型的简单数组
NewXXXArray系列函数如下:
  jbooleanArray NewBooleanArray (jsize val0)
  jbyteArray NewByteArray (jsize val0)
  jcharArray NewCharArray (jsize val0)
  jshortArray NewShortArray (jsize val0)
  jintArray NewIntArray (jsize val0)
  jlongArray NewLongArray (jsize val0)
  jfloatArray NewFloatArray (jsize val0)
  jdoubleArray NewDoubleArray (jsize val0)
 第一参数,jsize val0表示要创建的数组的大小.
SetXXXArrayRegion系列函数如下:
  void SetBooleanArrayRegion (jbooleanArray val0, jsize val1, jsize val2, jboolean * val3)
  void SetByteArrayRegion (jbyteArray val0, jsize val1, jsize val2, jbyte * val3)
  void SetCharArrayRegion (jcharArray val0, jsize val1, jsize val2, jchar * val3)
  void SetShortArrayRegion (jshortArray val0, jsize val1, jsize val2, jshort * val3)
  void SetIntArrayRegion (jintArray val0, jsize val1, jsize val2, jint * val3)
  void SetLongArrayRegion (jlongArray val0, jsize val1, jsize val2, jlong * val3)
  void SetFloatArrayRegion (jfloatArray val0, jsize val1, jsize val2, jfloat * val3)
  void SetDoubleArrayRegion (jdoubleArray val0, jsize val1, jsize val2, jdouble * val3)
参数的意义
表示把数组val0从val1开始的val2个元素设置为val3内存地址开始的val2个元素
GetXXXArrayRegion系列函数如下
  void GetBooleanArrayRegion (jbooleanArray val0, jsize val1, jsize val2, jboolean * val3)
  void GetByteArrayRegion (jbyteArray val0, jsize val1, jsize val2, jbyte * val3)
  void GetCharArrayRegion (jcharArray val0, jsize val1, jsize val2, jchar * val3)
  void GetShortArrayRegion (jshortArray val0, jsize val1, jsize val2, jshort * val3)
  void GetIntArrayRegion (jintArray val0, jsize val1, jsize val2, jint * val3)
  void GetLongArrayRegion (jlongArray val0, jsize val1, jsize val2, jlong * val3)
  void GetFloatArrayRegion (jfloatArray val0, jsize val1, jsize val2, jfloat * val3)
  void GetDoubleArrayRegion (jdoubleArray val0, jsize val1, jsize val2, jdouble * val3)
参数的意义
表示把数组val1从第val个元素开始的val2个元素拷贝到val3地址所指向的内存区域
对象数组
如果你需要对java对象数组的对象进行操作,你必须使用GetObjectArrayElement函数以jobject形式返回数组的元素,然后再操作jobject
你也可以用SetObjectArrayElement函数把jobject放进java对象数组,另外GetArrayLength函数能返回数组的长度。
关于对jobject的操作请参照后文。
如果想返回一个新的数组,可以先用NewObjectArray函数创建一个Java数组本地C/C++类型对象数组,然后通过SetObjectArrayElement函数设置数组元素(java对象),最后返回直接返回该数组就可以了。
关于如何创建在JNI中创建一个jobject(Java对象)请参照后文。
 jarray NewObjectArray (jsize val0, jclass cl1, jobject obj2)
第一参数,val0表示要创建的对象数组的大下。
第二参数,cl1表示创建的对象数组的元素是什么类型.
第三个参数,obj2表示数组元素的默认对象,一般用0表示null
 jobject GetObjectArrayElement (jobjectArray val0, jsize val1)
参数意义
表示取得val0数组的第val1个元素
 void SetObjectArrayElement (jobjectArray val0, jsize val1, jobject obj2)
参数意义
表示把val0数组的第val1个元素设置为对象obj2
另外,String数组当做一般的对象数组处理就可以了,只是String比普通的对象多了一些操作接口。
其实jstring只是jobject的一个子类,参看jni.h可知:
struct __jobject {};
struct __jclass : __jobject {};
struct __jstring : __jobject {};
示例
JNIEXPORT jobjectArray JNICALL Java_com_robin_HelloActivity_getStringArrayFromJni
(JNIEnv *env, jobject thiz)
{
    jstring      str;
    jobjectArray args = 0;
    jsize        len = 5;
    char*        sa[] = { "Hello,", "world!", "This", "is", "robin" };
    int          i=0;
    args = (env)->NewObjectArray(len,(env)->FindClass("java/lang/String"),0);
    for( i=0; i < len; i++ )
    {
        str = (env)->NewStringUTF(sa[i] );
        (env)->SetObjectArrayElement(args, i, str);
    }
    return args;
}
  评论这张
 
阅读(3734)| 评论(0)
推荐 转载

历史上的今天

在LOFTER的更多文章

评论

<#--最新日志,群博日志--> <#--推荐日志--> <#--引用记录--> <#--博主推荐--> <#--随机阅读--> <#--首页推荐--> <#--历史上的今天--> <#--被推荐日志--> <#--上一篇,下一篇--> <#-- 热度 --> <#-- 网易新闻广告 --> <#--右边模块结构--> <#--评论模块结构--> <#--引用模块结构--> <#--博主发起的投票-->
 
 
 
 
 
 
 
 
 
 
 
 
 
 

页脚

网易公司版权所有 ©1997-2017