JNI

JNI(Java Native Interface),它允许Java代码和其他语言写的代码进行交互。

JNI步骤:

  1. 创建一个类(MyJni.java)
  2. javac 编译该类
  3. javah -jni 产生头文件
  4. 编写本地代码,实现头文件中定义的方法。
  5. Run
public class MyJni {



    static {

        System.loadLibrary("myjni");

    }

    

    /*

     * 使用JNI的关键字native

     * 这个关键字决定我们那些方法能在我们的C文件中使用

     * 只须声明,不必实现

     */

    public native void sayHi(String name);

    

    public static native void add(int num);

    

    public static void main(String[] args) {

        new MyJni().sayHi(null);

        MyJni.add(100);

    }

    

}
F:\workspace\Learn\src>javac org\jni\MyJni.java
F:\workspace\Learn\src>javah -jni org.jni.MyJni

在 F:\workspace\Learn\src 下生成 org_jni_MyJni.h,代码如下:

/* DO NOT EDIT THIS FILE - it is machine generated */

#include <jni.h>

/* Header for class org_jni_MyJni */



#ifndef _Included_org_jni_MyJni

#define _Included_org_jni_MyJni

#ifdef __cplusplus

extern "C" {

#endif

/*

 * Class:     org_jni_MyJni

 * Method:    sayHi

 * Signature: (Ljava/lang/String;)V

 */

JNIEXPORT void JNICALL Java_org_jni_MyJni_sayHi

  (JNIEnv *, jobject, jstring);



/*

 * Class:     org_jni_MyJni

 * Method:    add

 * Signature: (I)V

 */

JNIEXPORT void JNICALL Java_org_jni_MyJni_add

  (JNIEnv *, jclass, jint);



#ifdef __cplusplus

}

#endif

#endif

编写 jni_MyJniImpl.c,

#include <jni.h>

#include "org_jni_MyJni.h"

#include <stdio.h>

JNIEXPORT void JNICALL Java_org_jni_MyJni_sayHi

(JNIEnv *env, jobject obj, jstring name)

{

    printf("From jni_MyJniImpl.c : sayHi. \n");

const jbyte *str;

    str = (*env)->GetStringUTFChars(env, name, NULL);

    if (str == NULL) {

        printf("the string is null.\n");

        return ; /* OutOfMemoryError already thrown */

    }

    printf("the string is %s.\n", str);

    return;

}



JNIEXPORT void JNICALL Java_org_jni_MyJni_add

(JNIEnv *env, jobject obj, jint num){

    printf("From jni_MyJniImpl.c : add. \n");

    return;

}

参数1 - JNIEnv自变量——它是指向类型为JNIEnv_的一个特殊JNI数据结构的指针。JNI数据结构的一个元素是指向由JVM生成的一个数组的指针;该数组的每个元素都是指向一个JNI函数的指针。可从固有方法的内部发出对JNI函数的调用,做法是撤消对这些指针的引用(具体的操作实际很简 单)。每种JVM都以自己的方式实现了JNI函数,但它们的地址肯定位于预先定义好的偏移处。

参数2 - 若方法是实例方法,则为jobject,相当于对象本身,即this。若是静态方法,则指向所在类 jclass。

编译生成动态库myjni.dll

gcc -Wall -D_JNI_IMPLEMENTATION_ -Wl,--kill-at -I F:\Java\jdk1.6.0_25\include –I F:\Java\jdk1.6.0_25\include\win32 -shared -o myjni.dll jni_MyJniImpl.c

运行JNI:把编译好的 dll 放到项目根目录,注意不是代码根目录。

 

你可能感兴趣的:(jni)