• <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  評(píng)論-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 }

            對(duì)編譯完的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類型和本地類型對(duì)應(yīng)
              
              在如下情況下,需要在本地方法中應(yīng)用java對(duì)象的引用,就會(huì)用到類型之間的轉(zhuǎn)換:
              
              1)java方法里面將參數(shù)傳入本地方法;
              
              2)在本地方法里面創(chuàng)建java對(duì)象;
              
              3)在本地方法里面return結(jié)果給java程序。
              
              分為如下兩種情況:
              
              Java原始類型
              
              像booleans、integers、floats等從Java程序中傳到本地方法中的原始類型可以直接使用,下面是java中的原始類型和本地方法中的類型的對(duì)應(yīng):
              
              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
              
              也就是說(shuō)如果我在方法中傳進(jìn)去了一個(gè)boolean的參數(shù)的話,那么我在本地方法中就有jboolean類型與之對(duì)應(yīng)。同理,如果在本地方法中return一個(gè)jint的話,那么在java中就返回一個(gè)int類型。 中國(guó)網(wǎng)管論壇
              
              Java對(duì)象
              
              Java對(duì)象做為引用被傳遞到本地方法中,所有這些Java對(duì)象的引用都有一個(gè)共同的父類型jobject(相當(dāng)于java中的Object類是所有類的父類一樣)。下面是JNI實(shí)現(xiàn)的一些jobject的子類:
              
              4.本地方法中訪問(wèn)java程序中的內(nèi)容
              
              1)訪問(wèn)String對(duì)象:
              
              從java程序中傳過(guò)去的String對(duì)象在本地方法中對(duì)應(yīng)的是jstring類型,jstring類型和c中的char*不同,所以如果你直接當(dāng)做char*使用的話,就會(huì)出錯(cuò)。因此在使用之前需要將jstring轉(zhuǎn)換成為c/c++中的char*,這里使用JNIEnv的方法轉(zhuǎn)換。下面是一個(gè)例子:
              
              代碼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方法將傳進(jìn)來(lái)的prompt(jstring類型)轉(zhuǎn)換成為UTF-8的格式,就能夠在本地方法中使用了。
              
              注意:在使用完你所轉(zhuǎn)換之后的對(duì)象之后,需要顯示調(diào)用ReleaseStringUTFChars方法,讓JVM釋放轉(zhuǎn)換成UTF-8的string的對(duì)象的空間,如果不顯示的調(diào)用的話,JVM中會(huì)一直保存該對(duì)象,不會(huì)被垃圾回收器回收,因此就會(huì)導(dǎo)致內(nèi)存溢出。

            www.bitsCN.com


              
              下面是訪問(wèn)String的一些方法:
              
              ◆GetStringUTFChars將jstring轉(zhuǎn)換成為UTF-8格式的char*
              
              ◆GetStringChars將jstring轉(zhuǎn)換成為Unicode格式的char*
              
              ◆ReleaseStringUTFChars釋放指向UTF-8格式的char*的指針
              
              ◆ReleaseStringChars釋放指向Unicode格式的char*的指針
              
              ◆NewStringUTF創(chuàng)建一個(gè)UTF-8格式的String對(duì)象
              
              ◆NewString創(chuàng)建一個(gè)Unicode格式的String對(duì)象
              
              ◆GetStringUTFLengt獲取UTF-8格式的char*的長(zhǎng)度
              
              ◆GetStringLength獲取Unicode格式的char*的長(zhǎng)度
              
              2) 訪問(wèn)Array對(duì)象:
              
              和String對(duì)象一樣,在本地方法中不能直接訪問(wèn)jarray對(duì)象,而是使用JNIEnv指針指向的一些方法來(lái)是用。
              
              訪問(wèn)Java原始類型數(shù)組:
              
              1)獲取數(shù)組的長(zhǎng)度:
              
              代碼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ù)組的長(zhǎng)度和普通的c語(yǔ)言中的獲取數(shù)組長(zhǎng)度不一樣,這里使用JNIEvn的一個(gè)函數(shù)GetArrayLength。
            bitsCN_com

              
              2)獲取一個(gè)指向數(shù)組元素的指針:
              
              代碼4:
              
              jint *body = (*env)->GetIntArrayElements(env, arr, 0);
              
              使用GetIntArrayElements方法獲取指向arr數(shù)組元素的指針,注意該函數(shù)的參數(shù),第一個(gè)是JNIEnv,第二個(gè)是數(shù)組,第三個(gè)是數(shù)組里面第三個(gè)是數(shù)組里面開(kāi)始的元素
              
              3)使用指針取出Array中的元素
              
              代碼5:
              
              for (i=0; i<len; i++) {
              sum += body[i];
              }
              
              這里使用就和普通的c中的數(shù)組使用沒(méi)有什么不同了
              
              4)釋放數(shù)組元素的引用
              
              代碼6:
              
              (*env)->ReleaseIntArrayElements(env, arr, body, 0);
              
              和操作String中的釋放String的引用是一樣的,提醒JVM回收arr數(shù)組元素的引用。
              
              這里舉的例子是使用int數(shù)組的,同樣還有boolean、float等對(duì)應(yīng)的數(shù)組。
              
              獲取數(shù)組元素指針的對(duì)應(yīng)關(guān)系:
              
              函數(shù)            數(shù)組類型
              
              GetBooleanArrayElements   boolean
              GetByteArrayElements    byte
              GetCharArrayElements    char bitsCN.nET中國(guó)網(wǎng)管博客
              GetShortArrayElements    short
              GetIntArrayElements     int
              GetLongArrayElements    long
              GetFloatArrayElements    float
              GetDoubleArrayElements   double
              
              釋放數(shù)組元素指針的對(duì)應(yīng)關(guān)系:
              Function            Array Type
              ReleaseBooleanArrayElements   boolean
              ReleaseByteArrayElements    byte
              ReleaseCharArrayElements    char
              ReleaseShortArrayElements    short
              ReleaseIntArrayElements     int
              ReleaseLongArrayElements    long
              ReleaseFloatArrayElements    float
              ReleaseDoubleArrayElements   double
              
              訪問(wèn)自定義Java對(duì)象數(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) 訪問(wèn)Java對(duì)象的方法:
              
              在本地方法中調(diào)用Java對(duì)象的方法的步驟:
              
              ①.獲取你需要訪問(wèn)的Java對(duì)象的類:
              
              jclass cls = (*env)->GetObjectClass(env, obj);
              
              使用GetObjectClass方法獲取obj對(duì)應(yīng)的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??>通過(guò)本地方法穿過(guò)來(lái)的jobject
              
              mid??>要調(diào)用的MethodID(即第二步獲得的MethodID)
              
              depth??>方法需要的參數(shù)(對(duì)應(yīng)方法的需求,添加相應(yīng)的參數(shù)) bitsCN.nET中國(guó)網(wǎng)管博客
              
              注:這里使用的是CallVoidMethod方法調(diào)用,因?yàn)闆](méi)有返回值,如果有返回值的話使用對(duì)應(yīng)的方法,在后面會(huì)提到。
              
              方法的Signature
              
              方法的Signature是由方法的參數(shù)和返回值的類型共同構(gòu)成的,下面是他們的結(jié)構(gòu):
              
              "(argument-types)return-type"
              
              其中Java程序中參數(shù)類型和其對(duì)應(yīng)的值如下:
              
              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
              
              一個(gè)Java類的方法的Signature可以通過(guò)javap命令獲取:
              
              javap -s -p Java類名
              
              給調(diào)用的函數(shù)傳參數(shù):
              
              通常我們直接在methodID后面將要傳的參數(shù)添加在后面,但是還有其他的方法也可以傳參數(shù):
              
              CallVoidMethodV可以獲取一個(gè)數(shù)量可變的列表作為參數(shù); www_bitscn_com
              
              CallVoidMethodA可以獲取一個(gè)union。
              
              調(diào)用靜態(tài)方法:
              
              就是將第二步和第三步調(diào)用的方法改為對(duì)應(yīng)的:
              
              GetStaticMethodID獲取對(duì)應(yīng)的靜態(tài)方法的ID
              
              CallStaticIntMethod調(diào)用靜態(tài)方法
              
              調(diào)用超類的方法:
              
              用的比較少,自己看啦。^_^。
              
              4)訪問(wèn)Java對(duì)象的屬性:
              
              訪問(wèn)Java對(duì)象的屬性和訪問(wèn)Java對(duì)象的方法基本上一樣,只需要將函數(shù)里面的Method改為Field即可





            posted on 2008-01-05 16:17 含笑半步癲 閱讀(993) 評(píng)論(0)  編輯 收藏 引用 所屬分類: java
            国产精品乱码久久久久久软件| 波多野结衣中文字幕久久| 国产精品美女久久久m| 亚洲精品无码久久久久去q | 无码久久精品国产亚洲Av影片| 久久久久久毛片免费看| 久久精品国产一区二区三区日韩| 99久久99久久精品免费看蜜桃| 婷婷五月深深久久精品| 久久精品无码专区免费东京热 | 久久99精品久久久久久齐齐| 99久久www免费人成精品| 国内精品久久久久久久coent | 久久精品成人国产午夜| 国产午夜精品理论片久久影视| 国产精品久久久久9999| 亚洲一区中文字幕久久| 少妇被又大又粗又爽毛片久久黑人| 精品久久久久久无码人妻蜜桃| 久久中文字幕无码专区| 久久人人爽人人爽人人片AV高清| 色偷偷久久一区二区三区| 国产精品9999久久久久| 9191精品国产免费久久| 亚洲国产成人精品久久久国产成人一区二区三区综| 国内精品免费久久影院| 久久91精品国产91久| 国产午夜免费高清久久影院| 国产精品免费看久久久香蕉| 久久这里的只有是精品23| 久久久久AV综合网成人| 久久亚洲国产成人影院网站| 亚洲人成精品久久久久| 国产激情久久久久影院小草| 久久久亚洲欧洲日产国码是AV| 久久亚洲欧美日本精品| 久久久久久久久久久久久久| 国产精品欧美久久久久无广告 | 久久国产色AV免费观看| 国内精品欧美久久精品| 久久棈精品久久久久久噜噜|