AndroidNDK开发(⼀)JNI简介及调⽤流程
前⾔
前段时间学习了C、C++的⼀些基础知识后,了解了它们的编码风格,要想掌握NDK开发,前提是会使⽤JNI,下⾯我们开始简单的介绍吧!
JNI简介
JNI全称是Java Native Interface(Java本地接⼝),本地接⼝就是指⽤C和C++开发的接⼝。从Java1.1开始,JNI标准成为java平台的⼀部分,它允许Java代码和其他语⾔写的代码进⾏交互。JNI⼀开始是为了本地已编译语⾔,尤其是C和C++⽽设计的,但是它并不妨碍你使⽤其他编程语⾔,只要调⽤约定受⽀持就可以了。
开发JNI程序会受到系统环境的限制,因为⽤C/C++语⾔写出来的代码或模块,编译过程当中要依赖当前操作系统环境所提供的⼀些库函数,并和本地库链接在⼀起。⽽且编译后⽣成的⼆进制代码只能在本地操作系统环境下运⾏,因为不同的操作系统环境,有⾃⼰的本地库和CPU指令集,⽽且各个平台对标准C/C++的规范和标准库函数实现⽅式也有所区别。这就造成使⽤了JNI接⼝的JAVA程序,不再像以前那样⾃由的跨平台。如果要实现跨平台,就必须将本地代码在不同的操作系统平台下编译出相应的动态库。
JNI的开发流程主要分为以下⼏个步骤:
1. 编写带有native声明⽅法的java类;
2. ⽤”javac”命令来编译所编写的java类;
3. 使⽤”javah”java类的名⽣成扩展名为h的头⽂件;
4. 复制jni.h和jni_md.h⽂件到CPP⼯程中;
5. 实现.h头⽂件中声明的函数
6. ⽣成dll动态链接库
7. 配置dll⽂件所在⽬录到环境变量
8. 重启Eclipse
jni调⽤dill的流程图如下:
通过上⾯的分析,相信⼤家已经对jni的开发流程有⼀个整体的认识,接下来,我们将通过实例更进⼀步的了解。
第⼀步:编写带有native声明⽅法的java类
JniTest.java
package com.study.jni;
public class JniTest {
public native static String getStringFromC();
}
第⼆步:⽤”javac”命令来编译所编写的java类;
⾸先我们必须得配有java环境变量,然后我们右键点击项⽬->properties,复制项⽬路径;
然后进⼊dos命令,
C:\Users\uuxuh>cd E:\Documents\11\JniTest
C:\Users\uuxuh>E:
E:\Documents\11\JniTest>cd src
E:\Documents\11\JniTest\src>
第三步:使⽤”javah”java类的名⽣成.h的头⽂件
接着,复制我们的完整类名(包名+类名),执⾏命令:
E:\Documents\11\JniTest\src>javah com.study.jni.JniTest
回到⼯程⽬录下,刷新项⽬,编译后的.h头⽂件就出现了。
源码:
com_study_jni_JniTest.h
/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class com_study_jni_JniTest */
#ifndef _Included_com_study_jni_JniTest
#define _Included_com_study_jni_JniTest
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: com_study_jni_JniTest
* Method: getStringFromC
* Signature: ()Ljava/lang/String;
*/
JNIEXPORT jstring JNICALL Java_com_study_jni_JniTest_getStringFromC
(JNIEnv *, jclass);
#ifdef __cplusplus
}
#endif
#endif
第四步:复制jni.h和jni_md.h⽂件到CPP⼯程中
将要编译的⽂件中引⼊了
#inlcude<jni.h>
头⽂件,所以我们⼿动导⼊这两个⽂件到CPP⼯程中,
以我的jdk1.7.0_75为例,两个头⽂件的位置分别为:
jni.h jdk1.7.0_75/include
jni_md.h jdk1.7.0_75/include/linux
将我们⽣成.h头⽂件复制到项⽬的代码⽂件⽬录下 , 在解决⽅案中的头⽂件⽬录-> 右键-> 添加 -> 添加现有项 。 将我们的头⽂件添加进来,还有jni.h和jni_md.h⼀起添加进来,如图:
第五步:实现.h头⽂件中声明的函数
c代码如下:
#include "com_study_jni_JniTest.h"
制作android软件流程//函数实现
JNIEXPORT jstring JNICALL Java_com_study_jni_JniTest_getStringFromC
(JNIEnv *env, j class jcls){
//简单的实现
//JNIEnv 结构体指针
//env⼆级指针
//代表Java运⾏环境,调⽤Java中的代码
//简单的实现
//将C的字符串转为⼀个java字符串
return (*env)->NewStringUTF(env, "C String");
}
第六步:⽣成dll动态链接库
我们以VS2013为例:
操作步骤:
选中项⽬ -> 右键 -> 属性 -> 常规 -> 项⽬默认值 -> 配置类型 , 选择动态库.dll,
如图,右上⾓配置管理器,根据我们所使⽤的平台进去配置⼀下:
这⾥我使⽤64位的,所以活动解决⽅案平台下新建了⼀个x64,部署项⽬配置也选择x64。配置完了之后,最后⽣成解决⽅案。去项⽬⽬录下查看dll动态库。
第七步:配置dll⽂件所在⽬录到环境变量
我们把⽣成dll⽂件的路径配置java环境变量⾥⾯,这样java 才会知道有dll动态库存在,配置完之后,
重启下Eclipse。最后我们在java中调⽤动态库,完整代码:
package com.study.jni;
public class JniTest {
public native static String getStringFromC();
public static void main(String[] args) {
System.out.println(getStringFromC());
}
// 加载动态库
static{
System.loadLibrary("jni_study");
}
}
最后运⾏⼀下项⽬控制台打印出C中返回给我们的字符串。
好了,整个jni的调⽤流程已经说的⾮常详细了,但这只是jni⼊门的基础,后续会继续更新!
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论