linux下JNI的demo
1.寫java文件
2.編譯java生成class
3.生成C/C++頭文件。
4.寫C/C++文件
5.編譯生成dll(Window下)或so文件
6.運(yùn)行java程序
下面介紹ubutun下一個JNI例子
1.編寫Sample1.java文件:
?? public class Sample1 { public native int intMethod(int n); public native boolean booleanMethod(boolean bool); public native String stringMethod(String text); public native int intArrayMethod(int[] intArray); public static void main(String[] args) { System.loadLibrary("Sample1"); Sample1 sample = new Sample1(); int square = sample.intMethod(5); boolean bool = sample.booleanMethod(true); String text = sample.stringMethod("JAVA"); int sum = sample.intArrayMethod( new int[]{1,1,2,3,5,8,13} ); System.out.println("intMethod: " + square); System.out.println("booleanMethod: " + bool); System.out.println("stringMethod: " + text); System.out.println("intArrayMethod: " + sum); } }
?兩個地方要注意,
?一。上面的方法都用到了native關(guān)鍵字。
?二。System.loadLibrary("Sample1");這句中"Sample1"是我們在第5步中得到的庫的名字,在window下是"Sample1.dll",在unix下要加前綴"lib",即"libSample1.so"。
?
2.編譯java文件:
javac ?Sample1.java
? ? 無錯生成Sample1.class文件
3.生成C/C++頭文件
javah ?Sample1
? ? 生成Sample1.h
使用命令 cat ?Sample1.h 查看,內(nèi)容為:
/* DO NOT EDIT THIS FILE - it is machine generated */ #include <jni.h> /* Header for class Sample1 */ #ifndef _Included_Sample1 #define _Included_Sample1 #ifdef __cplusplus extern "C" { #endif JNIEXPORT jint JNICALL Java_Sample1_intMethod (JNIEnv *, jobject, jint); JNIEXPORT jboolean JNICALL Java_Sample1_booleanMethod (JNIEnv *, jobject, jboolean); JNIEXPORT jstring JNICALL Java_Sample1_stringMethod (JNIEnv *, jobject, jstring); JNIEXPORT jint JNICALL Java_Sample1_intArrayMethod (JNIEnv *, jobject, jintArray); #ifdef __cplusplus } #endif #endif
?我們可以對比看看java文件中對應(yīng)的方法
?4.編寫C/C++代碼
???Sample1.c:
?#include "Sample1.h" #include <string.h> JNIEXPORT jint JNICALL Java_Sample1_intMethod (JNIEnv *env, jobject obj, jint num) { return num * num; } JNIEXPORT jboolean JNICALL Java_Sample1_booleanMethod (JNIEnv *env, jobject obj, jboolean boolean) { return !boolean; } JNIEXPORT jstring JNICALL Java_Sample1_stringMethod (JNIEnv *env, jobject obj, jstring string) { const char *str = (*env)->GetStringUTFChars(env, strin char cap[128]; strcpy(cap, str); (*env)->ReleaseStringUTFChars(env, string, str); return (*env)->NewStringUTF(env, strupr(cap)); } JNIEXPORT jint JNICALL Java_Sample1_intArrayMethod (JNIEnv *env, jobject obj, jintArray array) { int i, sum = 0; jsize len = (*env)->GetArrayLength(env, array); jint *body = (*env)->GetIntArrayElements(env, array, 0 for (i=0; i<len; i++) { sum += body[i]; } (*env)->ReleaseIntArrayElements(env, array, body, 0); return sum; } void main(){}
Sample1.cpp:#include "Sample1.h" #include <string.h> NIEXPORT jint JNICALL Java_Sample1_intMethod (JNIEnv *env, jobject obj, jint num) { return num * num; } JNIEXPORT jboolean JNICALL Java_Sample1_booleanMethod (JNIEnv *env, jobject obj, jboolean boolean) { return !boolean; } JNIEXPORT jstring JNICALL Java_Sample1_stringMethod (JNIEnv *env, jobject obj, jstring string) { const char *str = env->GetStringUTFChars(string, 0); char cap[128]; strcpy(cap, str); env->ReleaseStringUTFChars(string, str); return env->NewStringUTF(strupr(cap)); } JNIEXPORT jint JNICALL Java_Sample1_intArrayMethod (JNIEnv *env, jobject obj, jintArray array) { int i, sum = 0; jsize len = env->GetArrayLength(array); jint *body = env->GetIntArrayElements(array, 0); for (i=0; i<len; i++) { sum += body[i]; } env->ReleaseIntArrayElements(array, body, 0); return sum; } void main(){}
兩個差別就是JNIEnv這個類
? C中使用 jsize len = (*env)->GetArrayLength(env,array);
? C++中使用 jsize len = env->GetArrayLength(env,array); ?
?
5.生成共享庫文件
?編譯Sample1.c文件
?gcc -fPIC -D_REENTRANT -I/usr/lib/java/include -I/usr/lib/java/include/linux -c Sample1.c?
?編譯用到了jdk include中jni.h,include/linux中jni_md.h兩個頭文件
?/usr/lib/java/include ? ? ? ?是jin.h路徑
?/usr/lib/java/include、linux 是jni_md.h路徑
?此時生成Sampel.o文件
?運(yùn)行:
?gcc -shared Sample1.o -o libSample1.so
?生成libSample1.so
6.運(yùn)行java程序
libSample1.so文件拷貝到j(luò)ava的加載庫LD_LIBRARY_PATH指向的路徑中:
如果沒有足夠權(quán)限,可以這樣:
(1).在/home下建立一個用來存放.so庫文件的目錄,比如/home/xxx/lib
(2).把libSample1.so文件拷貝到該目錄下
(3).運(yùn)行:export LD_LIBRARY_PATH=/home/xxx/lib ?(只在當(dāng)前shall下有效...)
現(xiàn)在運(yùn)行java Sample1
一切正常后,可以看到運(yùn)行結(jié)果輸出:
intMethod: 25
booleanMethod: false
stringMethod: JAVA
intArrayMethod: 33
完成第一個JNI程序。
總結(jié)
以上是生活随笔為你收集整理的linux下JNI的demo的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 对提高squid命中率的一些研究
- 下一篇: Log4net 在framework C