1.网上很多关于jni的入门代码都没有指明操作环境造成了理解上的很不方便,下面我记录下在mac上的操作过程,并且对一些步骤作简单说明
2.编写java文件,并且编译
java代码如下
public class Native{
//这里定义native方法,native方法不能有方法体
public native say();
}
public class Main{
static{
//这里加载相应的库文件,库文件的名字要和动态库匹配,这里动态库文件为libnative.jnilib
System.loadLibrary("native");
}
public static void main(String[] args){
Native n=new Native();
n.say();
}
}
然后需要编译java代码 javac Main.java 然后会生成Main.class
3.生成Native头文件,头文件是javah这个工具生成的,生成的.h文件里面包含了native函数的格式,这时候需要自己编写一个.cpp文件来实现这个方法
生成.h文件:javah Native.java
Native.h的内容
/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class Native */
#ifndef _Included_Native
#define _Included_Native
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: Native
* Method: say
* Signature: ()V
*/
JNIEXPORT void JNICALL Java_Native_say
(JNIEnv *, jobject);
#ifdef __cplusplus
}
#endif
#endif
Native.cpp的内容
#include "Native.h"
#include <iostream>
using namespace std;
JNIEXPORT void JNICALL Java_Native_say
(JNIEnv *, jobject){
cout<<"Hello world"<<endl;
}
4.生成动态库
这个操作可以分成两步,第一步生成.o文件,第二步生成.jnilib文件
第一步的指令: g++ -I /Users/kisstheraik/jdk1.8.0_101/include -I /Users/kisstheraik/jdk1.8.0_101/include/linux -c Native.cpp
这里需要说明的是 -I指明了头文件的搜索路径(因为这里Native.h里面有个jni.h需要知道位置),-c告诉编译器这一步只编译不链接,不然可能会报错。这里会生成Native.o文件
第二步的指令: g++ -dynamiclib -o libnative.jnilib Native.o
这里需要说明的是注意库的名字,并且一定记得后缀是jnilib,网上有很多mac平台教程的后缀都是so,我真不知道他们怎么做出来的
5.运行
从前面的代码中我们可以看到程序会加载libnative.jnilib这个库文件,加载路径实际上是一个名为“java.library.path”所指定的路径,这个路径包括了当前路径,因此不需要做改动就能运行。当然如果你的libnative.jnilib在其他地方记的把路径加到java.library.path变量里面。
运行: java Main