• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            隨筆-30  評論-67  文章-0  trackbacks-0



            編譯HelloWorld類
             1 public class HelloWorld {
             2     public native void displayHelloWorld();
             3 
             4     public native void printxx(String str);
             5 
             6     static {
             7         System.loadLibrary("hello");
             8         // System.load("hello");
             9     }
            10 
            11     public static void main(String[] args) {
            12         HelloWorld hw = new HelloWorld();
            13         hw.displayHelloWorld();
            14         for (int i = 0;; ++i) {
            15             hw
            16                     .printxx("wo kaowo kaowo kaowo kaowo kaowo kaowo kaowo kaowo kaowo kaowo kao");
            17             if (i % 1000 == 0) {
            18                 try {
            19                     Thread.sleep(10);
            20                 } catch (InterruptedException e) {
            21                 }
            22             }
            23         }
            24     }
            25 }

            對編譯完的class執(zhí)行
            javah HelloWorld

             1 /* DO NOT EDIT THIS FILE - it is machine generated */
             2 #include <jni.h>
             3 /* Header for class HelloWorld */
             4 
             5 #ifndef _Included_HelloWorld
             6 #define _Included_HelloWorld
             7 #ifdef __cplusplus
             8 extern "C" {
             9 #endif
            10 /*
            11  * Class:     HelloWorld
            12  * Method:    displayHelloWorld
            13  * Signature: ()V
            14  */
            15 JNIEXPORT void JNICALL Java_HelloWorld_displayHelloWorld
            16   (JNIEnv *, jobject);
            17 
            18 /*
            19  * Class:     HelloWorld
            20  * Method:    printxx
            21  * Signature: (Ljava/lang/String;)V
            22  */
            23 JNIEXPORT void JNICALL Java_HelloWorld_printxx
            24   (JNIEnv *, jobject, jstring);
            25 
            26 #ifdef __cplusplus
            27 }
            28 #endif
            29 #endif
            30 

            編譯
            cl -I%java_home%\include -I%java_home%\include\win32 -LDHelloWorld.c -Fehello.dll

             1 #include <jni.h>
             2 #include "HelloWorld.h"
             3 #include <stdio.h>
             4 JNIEXPORT void JNICALL Java_HelloWorld_displayHelloWorld(JNIEnv *env, jobject obj)
             5 {
             6 printf("Hello world!\n"); 
             7 return;
             8 }
             9 
            10 JNIEXPORT void JNICALL Java_HelloWorld_printxx
            11   (JNIEnv *env, jobject obj, jstring prompt){
            12 
            13 const char *str = (*env)->GetStringUTFChars(env, prompt, 0);
            14   printf("%s",prompt);
            15 (*env)->ReleaseStringUTFChars(env, prompt, str);
            16   
            17   return;
            18   }
            19   
            20   




            3.Java類型和本地類型對應
              
              在如下情況下,需要在本地方法中應用java對象的引用,就會用到類型之間的轉(zhuǎn)換:
              
              1)java方法里面將參數(shù)傳入本地方法;
              
              2)在本地方法里面創(chuàng)建java對象;
              
              3)在本地方法里面return結果給java程序。
              
              分為如下兩種情況:
              
              Java原始類型
              
              像booleans、integers、floats等從Java程序中傳到本地方法中的原始類型可以直接使用,下面是java中的原始類型和本地方法中的類型的對應:
              
              Java類型  本地類型  字節(jié)(bit)
              
              boolean   jboolean   8, unsigned
              byte    jbyte    8
              char    jchar    16, unsigned
              short    jshort    16
              int     jint     32
              long    jlong    64
              float    jfloat    32
              double   jdouble   64
              void    void     n/a
              
              也就是說如果我在方法中傳進去了一個boolean的參數(shù)的話,那么我在本地方法中就有jboolean類型與之對應。同理,如果在本地方法中return一個jint的話,那么在java中就返回一個int類型。 中國網(wǎng)管論壇
              
              Java對象
              
              Java對象做為引用被傳遞到本地方法中,所有這些Java對象的引用都有一個共同的父類型jobject(相當于java中的Object類是所有類的父類一樣)。下面是JNI實現(xiàn)的一些jobject的子類:
              
              4.本地方法中訪問java程序中的內(nèi)容
              
              1)訪問String對象:
              
              從java程序中傳過去的String對象在本地方法中對應的是jstring類型,jstring類型和c中的char*不同,所以如果你直接當做char*使用的話,就會出錯。因此在使用之前需要將jstring轉(zhuǎn)換成為c/c++中的char*,這里使用JNIEnv的方法轉(zhuǎn)換。下面是一個例子:
              
              代碼3:
              
              JNIEXPORT jstring JNICALL Java_Prompt_getLine
              (JNIEnv *env, jobject obj, jstring prompt)
              {
              char buf[128];
              const char *str = (*env)->GetStringUTFChars(env, prompt, 0);
              printf("%s", str);
              (*env)->ReleaseStringUTFChars(env, prompt, str);
              
              這里使用GetStringUTFChars方法將傳進來的prompt(jstring類型)轉(zhuǎn)換成為UTF-8的格式,就能夠在本地方法中使用了。
              
              注意:在使用完你所轉(zhuǎn)換之后的對象之后,需要顯示調(diào)用ReleaseStringUTFChars方法,讓JVM釋放轉(zhuǎn)換成UTF-8的string的對象的空間,如果不顯示的調(diào)用的話,JVM中會一直保存該對象,不會被垃圾回收器回收,因此就會導致內(nèi)存溢出。

            www.bitsCN.com


              
              下面是訪問String的一些方法:
              
              ◆GetStringUTFChars將jstring轉(zhuǎn)換成為UTF-8格式的char*
              
              ◆GetStringChars將jstring轉(zhuǎn)換成為Unicode格式的char*
              
              ◆ReleaseStringUTFChars釋放指向UTF-8格式的char*的指針
              
              ◆ReleaseStringChars釋放指向Unicode格式的char*的指針
              
              ◆NewStringUTF創(chuàng)建一個UTF-8格式的String對象
              
              ◆NewString創(chuàng)建一個Unicode格式的String對象
              
              ◆GetStringUTFLengt獲取UTF-8格式的char*的長度
              
              ◆GetStringLength獲取Unicode格式的char*的長度
              
              2) 訪問Array對象:
              
              和String對象一樣,在本地方法中不能直接訪問jarray對象,而是使用JNIEnv指針指向的一些方法來是用。
              
              訪問Java原始類型數(shù)組:
              
              1)獲取數(shù)組的長度:
              
              代碼4:
              
              JNIEXPORT jint JNICALL Java_IntArray_sumArray
              (JNIEnv *env, jobject obj, jintArray arr)
              {
              int i, sum = 0;
              jsize len = (*env)->GetArrayLength(env, arr);
              
              如代碼4所示,這里獲取數(shù)組的長度和普通的c語言中的獲取數(shù)組長度不一樣,這里使用JNIEvn的一個函數(shù)GetArrayLength。
            bitsCN_com

              
              2)獲取一個指向數(shù)組元素的指針:
              
              代碼4:
              
              jint *body = (*env)->GetIntArrayElements(env, arr, 0);
              
              使用GetIntArrayElements方法獲取指向arr數(shù)組元素的指針,注意該函數(shù)的參數(shù),第一個是JNIEnv,第二個是數(shù)組,第三個是數(shù)組里面第三個是數(shù)組里面開始的元素
              
              3)使用指針取出Array中的元素
              
              代碼5:
              
              for (i=0; i<len; i++) {
              sum += body[i];
              }
              
              這里使用就和普通的c中的數(shù)組使用沒有什么不同了
              
              4)釋放數(shù)組元素的引用
              
              代碼6:
              
              (*env)->ReleaseIntArrayElements(env, arr, body, 0);
              
              和操作String中的釋放String的引用是一樣的,提醒JVM回收arr數(shù)組元素的引用。
              
              這里舉的例子是使用int數(shù)組的,同樣還有boolean、float等對應的數(shù)組。
              
              獲取數(shù)組元素指針的對應關系:
              
              函數(shù)            數(shù)組類型
              
              GetBooleanArrayElements   boolean
              GetByteArrayElements    byte
              GetCharArrayElements    char bitsCN.nET中國網(wǎng)管博客
              GetShortArrayElements    short
              GetIntArrayElements     int
              GetLongArrayElements    long
              GetFloatArrayElements    float
              GetDoubleArrayElements   double
              
              釋放數(shù)組元素指針的對應關系:
              Function            Array Type
              ReleaseBooleanArrayElements   boolean
              ReleaseByteArrayElements    byte
              ReleaseCharArrayElements    char
              ReleaseShortArrayElements    short
              ReleaseIntArrayElements     int
              ReleaseLongArrayElements    long
              ReleaseFloatArrayElements    float
              ReleaseDoubleArrayElements   double
              
              訪問自定義Java對象數(shù)組
              
              The JNI provides a separate set of functions to access elements of object arrays. You can use these functions to get and set individual object array elements.
              
              Note: You cannot get all the object array elements at once.
              
              GetObjectArrayElement returns the object element at a given index.
            www_bitscn_com

              
              SetObjectArrayElement updates the object element at a given index.
              
              3) 訪問Java對象的方法:
              
              在本地方法中調(diào)用Java對象的方法的步驟:
              
              ①.獲取你需要訪問的Java對象的類:
              
              jclass cls = (*env)->GetObjectClass(env, obj);
              
              使用GetObjectClass方法獲取obj對應的jclass。
              
              ②.獲取MethodID:
              
              jmethodID mid = (*env)->GetMethodID(env, cls, "callback", "(I)V");
              
              使用GetMethdoID方法獲取你要使用的方法的MethdoID。其參數(shù)的意義:
              
              env??>JNIEnv
              
              cls??>第一步獲取的jclass
              
              "callback"??>要調(diào)用的方法名
              
              "(I)V"??>方法的Signature
              
              ③.調(diào)用方法:
              
              (*env)->CallVoidMethod(env, obj, mid, depth);
              
              使用CallVoidMethod方法調(diào)用方法。參數(shù)的意義:
              
              env??>JNIEnv
              
              obj??>通過本地方法穿過來的jobject
              
              mid??>要調(diào)用的MethodID(即第二步獲得的MethodID)
              
              depth??>方法需要的參數(shù)(對應方法的需求,添加相應的參數(shù)) bitsCN.nET中國網(wǎng)管博客
              
              注:這里使用的是CallVoidMethod方法調(diào)用,因為沒有返回值,如果有返回值的話使用對應的方法,在后面會提到。
              
              方法的Signature
              
              方法的Signature是由方法的參數(shù)和返回值的類型共同構成的,下面是他們的結構:
              
              "(argument-types)return-type"
              
              其中Java程序中參數(shù)類型和其對應的值如下:
              
              Signature  Java中的類型
              Z       boolean
              B       byte
              C       char
              S       short
              I       int
              J       long
              F       float
              D       double
              L fully-qualified-class;   fully-qualified-class
              
              [ type  type[]
              
              ( arg-types ) ret-type  method type
              
              一個Java類的方法的Signature可以通過javap命令獲取:
              
              javap -s -p Java類名
              
              給調(diào)用的函數(shù)傳參數(shù):
              
              通常我們直接在methodID后面將要傳的參數(shù)添加在后面,但是還有其他的方法也可以傳參數(shù):
              
              CallVoidMethodV可以獲取一個數(shù)量可變的列表作為參數(shù); www_bitscn_com
              
              CallVoidMethodA可以獲取一個union。
              
              調(diào)用靜態(tài)方法:
              
              就是將第二步和第三步調(diào)用的方法改為對應的:
              
              GetStaticMethodID獲取對應的靜態(tài)方法的ID
              
              CallStaticIntMethod調(diào)用靜態(tài)方法
              
              調(diào)用超類的方法:
              
              用的比較少,自己看啦。^_^。
              
              4)訪問Java對象的屬性:
              
              訪問Java對象的屬性和訪問Java對象的方法基本上一樣,只需要將函數(shù)里面的Method改為Field即可





            posted on 2008-01-05 16:17 含笑半步癲 閱讀(1010) 評論(0)  編輯 收藏 引用 所屬分類: java
            亚洲欧美日韩精品久久| 伊人久久精品影院| 91亚洲国产成人久久精品| 国产精品伦理久久久久久| 亚洲精品成人网久久久久久| 亚洲级αV无码毛片久久精品| 久久99国产精品久久99| 国内精品久久久久影院老司| 99久久精品国产麻豆| 亚洲美日韩Av中文字幕无码久久久妻妇 | 亚洲日韩中文无码久久| 四虎国产精品免费久久5151 | 午夜精品久久久久久99热| 国产99久久久久久免费看| 少妇精品久久久一区二区三区| 久久人人爽人人精品视频| 日本精品久久久中文字幕| 无码精品久久久天天影视| 亚洲精品乱码久久久久久蜜桃 | 亚洲嫩草影院久久精品| 久久综合亚洲欧美成人| 久久夜色精品国产亚洲| 精品无码久久久久久久久久| 久久99中文字幕久久| 久久国产热精品波多野结衣AV | 国产三级精品久久| 伊人久久大香线蕉精品| 精品国产91久久久久久久| 久久久噜噜噜久久熟女AA片| 色欲综合久久躁天天躁蜜桃| 亚洲精品乱码久久久久久按摩| 久久狠狠爱亚洲综合影院 | 日韩人妻无码一区二区三区久久| 久久婷婷五月综合色奶水99啪| 日本加勒比久久精品| 人妻无码久久精品| 久久人做人爽一区二区三区| 日韩精品无码久久久久久| 99久久久精品免费观看国产| 欧美亚洲另类久久综合| 久久久精品国产亚洲成人满18免费网站 |