JNI编程基础

JNI基础概念
     Java Native Interface   Java本地调用  主要是为了和C/C++交互
        

JNI的副作用
一旦使用JNI,JAVA程序就丧失了JAVA平台的两个优点:
1、程序不再跨平台。要想跨平台,必须在不同的系统环境下重新编译本地语言部分。
2、程序不再是绝对安全的,本地代码的不当使用可能导致整个程序崩溃。一个通用规则是,你应该让本地方法集中在少数几个当中。这样就降低了JAVA和C之间的耦合性


    
    



JNI操作函数



JNI异常

如果出现java.lang.UnsatisfiedLinkError的异常,解决方法如下:
1.java -Djava.library.path
2.export LD_LIBRARY_PATH

操作实例:
1.编写    TestJni.java
  1. public class TestJin{
  2. //定义的一个native方法,并加载动态库
  3. public native void print(String str);
  4. static{
  5. System.loadLibrary("MyJni");
  6. }
  7. public static void main(String[] args){
  8. new TestJin().print("hello jni");
  9. }
  10. }
2.编译     javac TestJin.java
3.生成头文件    javah -jni TestJni
4.重命名 mv TestJni.h MyJni.h
5.添加修改代码 MyJni.h
  1. #include<MyJni.h>
  2. #include<stdio.h>
  3. /* Header for class TestJni*/
  4. #ifndef _Included_TestJni
  5. #define _Included_TestJni
  6. #ifdef __cplusplus
  7. extern "C"{
  8. #endif
  9. JNIEXPORT void JNICALL Java_TestJni_print
  10. (JNIEnv *env, jobject obj, jstring str){
  11. jchar *s =(jchar *)(*env) ->GetStringUTFChars(env,str,NULL);
  12. printf("content is %s\n",(char *)s);
  13. (*env)->ReleaseStringUTFChars(env,str,(const char*)s);
  14. }
  15. #ifdef __cplusplus
  16. }
  17. #endif
  18. #endif
  19. /*
  20. 1.JNIEnv是JNI的核心数据,指向JNIEnv结构的指针
  21. 2.jobject的意义取决于该方法是否是静态还是实例方法。当本地方法作为一个实例方法时,第二个参数相当于对象本身,即this.当本地方法作为一个静态方法时,指向所在类。
  22. 3.jni.h文件必须被包含,该文件定义了JNI所有的函数声明和数据类型。
  23. 4.JNIEXPORT和JNICALL是可忽略的JNI关键字,其实是一些宏,想了解的可以找jni_md.h文件查看。我们目前使用的jni.h定义他们为空。
  24. */

6.执行命令生成 libMyJni.so文件
gcc -fPIC -shared -o libMyJni.so MyJni -I. -I/home/dir -I/%JAVA_HOME%



1)JNI
    java code 与 c/c++进行交互
2)JNI编程流程
        a. 编写一个.java
        b.javac *.java
        c.javah -jni className -> *.h
        d.在.c/.cpp文件实现这个native方法
        e.创建一个.so/.dll
3)数据类型
        char -> jchar boolean -> jboolean ...
4)出现java.lang.UnsatifiedLinkedError的异常
        java -Djava.library.path
        export LD_LIBRARY_PATH
5)注意事项
    a.不要直接使用从Java里面传递过来的对象,基本数据类型,要用过环境指针转换 (*env) ->
    b.一旦不使用某个对象或变量,要去释放内存release
    c.不要在native code里面去申请内存
JNI签名
    可以通过javap -s 查看类的签名
JNI签名类型
   






posted @ 2015-07-03 11:31  登高一呼  阅读(271)  评论(0编辑  收藏  举报