您的位置:首页 > 移动开发 > Android开发

Java调用库文件(JNI)(android对此有所改变)

2016-05-17 16:55 204 查看
1.准备java 程序

testdll.java,内容为:

public class testdll {

static {

System.loadLibrary("goodluck"); //载入库名,库的扩展名字究竟是DLL还是SO,由系统自己判断。

}

//还需对将要调用的方法做本地声明,关键字为native。且只需要声明,而不需要具体实现

public native static int get();

public native static void set(int i);

public static void main(String[] args) {

testdll test = new testdll();

test.set(10);

System.out.println(test.get());

}

}

然后编译该JAVA程序文件,生成CLASS,再用JAVAH命令,JNI就会生成C/C++的头文件。

用javac testdll.java编译它,会生成testdll.class。

再用javah testdll,则会在当前目录下生成testdll.h文件,内容如下:

#include

#ifndef _Included_testdll

#define _Included_testdll

#ifdef __cplusplus

extern "C" {

#endif

JNIEXPORT jint JNICALL Java_testdll_get (JNIEnv *, jclass);

JNIEXPORT void JNICALL Java_testdll_set (JNIEnv *, jclass, jint);

#ifdef __cplusplus

}

#endif

#endif

在具体实现的时候,我们只关心两个函数原型

JNIEXPORT jint JNICALL Java_testdll_get (JNIEnv *, jclass); 和

JNIEXPORT void JNICALL Java_testdll_set (JNIEnv *, jclass, jint);

这里JNIEXPORT和JNICALL都是JNI的关键字,函数的名称是JAVA_再加上java程序的package路径再加函数名组成的。

下面我们用testdll.cpp文件具体实现这两个函数;

#include "testdll.h"

int i = 0;

JNIEXPORT jint JNICALL Java_testdll_get (JNIEnv *, jclass)

{

return i;

}

JNIEXPORT void JNICALL Java_testdll_set (JNIEnv *, jclass, jint j)

{

i = j;

}

编译连接成库文件,本例是在WINDOWS下做的,生成的是DLL文件,名字为goodluck.dll。把goodluck.dll拷贝到testdll.class的目录下(或者加入环境变量中),java testdll运行它。

对于最重要得参数传递,字长不一样,因此,需要转换。比如传递字符串,java文件中参数为byte[] param,c文件中为jbyteArray,转换可以如下进行:

jsize theArrayLengthJ = (*env)->GetArrayLength(env,param); //得到本地字长

jbyte * arrayBody = (*env)->GetByteArrayElements(env,param,0);//得到本地元素

char* str=(char *)arrayBody;

main中:

byte[] temp = {0}; //字符串末尾补0

String str= "早上好";

byte[] bb= str.getBytes("gbk");

byte[] lastBB = new byte[str.length + temp.length]; //得到最终要传递得参数

就是在传递字节数组到C程序中时,最后的结尾一定要以0结束。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: