JNI随笔
有word文档格式清晰。
懒得腾上来,直接粘贴上来的,格式就乱了!
https://files.cnblogs.com/LeeCe/JNI%e5%ae%9e%e8%b7%b5.rar
而且文档里有源代码。
全面学习技术要看官方说明书
http://download.oracle.com/javase/1.4.2/docs/guide/jni/JNI官方文档 看了一点,东西太多…
http://java.sun.com/developer/onlineTraining/Programming/JDCBook/jniexamp.html#examp oracle官方
http://www.docin.com/p-19086932.html#documentinfo 葵花宝典 <- 这个好
http://hi.baidu.com/pjdashu/blog/item/5e54df9961040d006e068c1b.html 葵花宝典 <- 这个好
http://www.docin.com/p-57861959.html Java JNI 完全手册
http://www.docin.com/p-46800196.html JNI_编程技术__网文整理 <- 这个很乱
JNI步骤
3种互调类型
java调c程序
过程:
Java类转成个.h -> VC实现.h,生成.dll -> Java使用.dll
生成.h:
写个类,包含所有c中准备实现的方法的签名(签名:只有函数头,没有函数体)。
方法1,2编译时有区别:
方法1:练习
1> 建立d:/TestClass.java空文件, 内容如下:
public class TestClass {
public native void functionA();
}
2> dos下进入d:/ , javac TestClass.java生成TestClass.class, javahTestClass生成 TestClass.h
注意:如果文件名与类名不同,则类前部能带public。涉及的基本概念,,,忘记了。
例如:1’建立d:/abc.java,内容如下:
class TestClass {
public native void functionA();
}
2’dos下进入d:/ , javac abc.java生成TestClass.class, javahTestClass生成 TestClass.h
3> 结果
方法2: 更像真实的使用环境结构。
1> netbeans建立项目:名称jnitest, 创建主类打勾。结果:生成一个包jnitest,包里有一个Main类文件。
2> 在包jnitest下,新建类文件TestClass,把方法签名写进去就成了:
package jnitest;
public class TestClass {
public native void functionA();
}
3> dos下进入..\jnitest\src\jnitest所在的文件层, javacTestClass.java生成TestClass.class,
4> dos下退一层到 ..\jnitest\src\, javahjnitest.TestClass生成 jnitest_TestClass.h。
注意: 必须退到和jnitest包一层进行生成才可以。 与TestClass同层,无论是javah TestClass还是javahjnitest.TestClass都不可以。
5> 结果
生成dll:
- VS建立mfc dll工程
命名capi , 选第2个静态库,底下空(按F1弹出相应内容解释)。
- 加入TestClass.h
先看一看TestClass.h的内容:
注意:看到有个#include”jni.h”这在MFC DLL工程里是没有的,而是javajdk提供的,在jdk目录下的include文件夹下。
Jni.h中保存了所有java jni提供函数接口,函数类型。这些内容通过JNIEnv来调用。方便c和java的交互。
下面我们先配置jni.h和与他关联的.h所在的目录。
- 3. 配置jni.h目录
写c的人都会,写java的看不懂,可以到网上搜下。
在项目上右键,最下面“属性“,添加两个头文件目录:
- 4. 创建空文件TestClass.cpp
对方法进行实现:
#include "stdafx.h"
#include "stdafx.h"
#include "jnitest_TestClass.h"
#include <iostream>
#include "stdlib.h"
#include "string.h"
using namespace std;
JNIEXPORT voidJNICALL Java_jnitest_TestClass_functionA(JNIEnv *, jobject)
{
cout<< "HI! JIN"<<endl;
}
注意:别拉掉 #include "stdafx.h"
- 5. 生成capi.dll
点生成项目, 然后到Debug或release文件夹中 找 capi.dll文件。
使用dll:
- 将capi.dll 放到 %java_home%\bin 或%java_home%\jre\bin 或 项目根目录下均成。
- 测试, 用第一步建立的jnitest项目, 在Main函数里写如下内容:
public class Main {
public static void main(String[] args) {
System.loadLibrary("capi");
TestClass a = newTestClass();
a.functionA();
}
}
注意:用第一步建立的jnitest项目的关键点有两个。
1. TestClass那一套还要有 2. 要有System.loadLibrary("capi")读入dll文件;
- 结果
c实现中调用java
不是纯粹的,在c中如何调用java。
而是Java调c程序的c函数实现中,通过两个参数(JNIEnv *, jobject)调用java函数辅助实现c函数。
c独立调用java
http://public0821.javaeye.com/blog/423941 新经典
http://tech.ccidnet.com/art/1081/20050413/237901_2.html 老经典
1. 写java类,方法
把需要在c中调用的方法,写成java类:
编译:
?后面在由 (这里还有疑问)
options[1].optionString= "-Djava.class.path=.;d:\\";
jclass cls = env->FindClass("test/Demo");
共同决定位置
2. 创建c项目
1) 2个附加目录设置,1个附加库设置,jdkXXX\include, jdXXX\include\win32, jdk\lib.
2) 初始化虚拟机
- options指定调用类的位置
- res = (*funCreateJavaVM)(&jvm, (void**)&env, &vm_args);
创建虚拟机, 初始化jni事件(JNIEnv * env),用利用env来调用jni的各种方法以调用java类方法。
3) 使用(JNIEnv * env)调用java各个类,以及相应方法。
jclass cls = env->FindClass("test/Demo");
调用类,寻找类,使用其方法。
- 3. 关闭虚拟机
浙公网安备 33010602011771号