java JNI 静态和动态注册的区别
sheshizhang关注赞赏支持java JNI 静态和动态注册的区别
静态注册
原理:根据函数名来建立 java 方法与 JNI 函数的一一对应关系;
实现流程:
编写 java 代码;
利用 javah 指令生成对应的 .h 文件;
对 .h 中的声明进行实现;
弊端:
编写不方便,JNI 方法名字必须遵循规则且名字很长;
编写过程步骤多,不方便;
程序运行效率低,因为初次调用native函数时需要根据根据函数名在JNI层中搜索对应的本地函数,然后建立对应关系,这个过程比较耗时;
动态注册
原理:利用 RegisterNatives 方法来注册 java 方法与 JNI 函数的一一对应关系;
实现流程:
利用结构体 JNINativeMethod 数组记录 java 方法与 JNI 函数的对应关系;
实现 JNI_OnLoad 方法,在加载动态库后,执行动态注册;
调用 FindClass 方法,获取 java 对象;
调用 RegisterNatives 方法,传入 java 对象,以及 JNINativeMethod 数组,以及注册数目完成注册;
动态注册方式:
1:第一步先实现JNI_OnLoad方法(利用 RegisterNatives 方法来注册 java 方法与 JNI 函数的一一对应关系)
static const char* mClassName="com/demo/jnitest/MainActivity";
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO, LOG_TAG, __VA_ARGS__)extern "C" JNIEXPORT jint JNICALL
JNI_OnLoad(JavaVM *vm,void *reserved){
LOGI("JNI_OnLoad");
_vm=vm;
JNIEnv *jniEnv;
jint r = vm->GetEnv((void**)&jniEnv, JNI_VERSION_1_6);
if (r!=JNI_OK){
return -1;
}
jclass pJclass = jniEnv->FindClass(mClassName);
if(pJclass==NULL){
printf("cannot get class:%s\n", mClassName);
return -1;
}
//注册
jniEnv->RegisterNatives(pJclass,getMethod, sizeof(getMethod)/sizeof(JNINativeMethod));
return JNI_VERSION_1_6;
}
2:利用结构体 JNINativeMethod 数组记录 java 方法与 JNI 函数的对应关系
static const JNINativeMethod getMethod[]{
{"javaAdd","(II)I",(jint *)C_Add},
};
其中testThread是在Activity页面声明好的native函数。
public native int javaAdd(int a,int b);
方法初始化调用:
extern "C" JNIEXPORT jint JNICALL
C_Add(JNIEnv *env,
jobject jobject1,
jint a,
jint b){
return a+b;
}
推荐阅读更多精彩内容
- 2.JNI.h解析 什么是JNI? JNI 是java本地开发接口.JNI 是一个协议,这个协议用来沟通java代码和外部的本地代码(... a_tomcat阅读 1,008评论 0 赞 51
- [转] Android JNI 作用及其详解 _ 声明: 对原文格式以及内容做了细微的修改和美化, 主要为了方便阅读和理解 _ 一. 基础 Java Nativ... 元亨利贞o阅读 3,319评论 0 赞 32
- JNI入门了解 什么是JNI? JNI Java Native Interface java本地接口 JNI 能够解决什么问题? ... 安仔夏天勤奋阅读 134评论 0 赞 1
- Android逆向新手答疑解惑篇——JNI与动态注册 何为JNI JNI全称为Java Native Interface,是使Java方法与C\C++函数互通的一座桥梁... 看雪学院阅读 428评论 1 赞 1
- Android JNI学习(三)——Java与Native相互调用 本系列文章如下: Android JNI(一)——NDK与JNI基础Android JNI学习(二)——实战JNI... 隔壁老李头阅读 20,634评论 6 赞 42