Android JNI學習06-AndroidStudio3.6 JNI函數更新java層的數組

鏈接:https://pan.baidu.com/s/1zB9r5WwuTMIPNMlYl5HlvA 
提取碼:5ndl

本篇以下篇的代碼爲例,實現在JNI函數裏更新java層的數組,沒有看過下篇的朋友,可以先去看下。

Android JNI學習04-AndroidStudio3.6 java 向 C++函數傳遞數組

在MainActivity中調用sendIntArrayToJNI

sendIntArrayToJNI對應的JNI函數內容如下

extern "C"
JNIEXPORT jstring JNICALL
Java_com_example_jnistudy_MainActivity_sendIntArrayToJNI(JNIEnv *env, jobject thiz,
        jintArray int_array) {
    jint *javaArray = env->GetIntArrayElements(int_array, NULL);
    int32_t length = env->GetArrayLength(int_array);
    for (int k = 0; k < length; ++k) {
        int tmp = *(javaArray+k);
        __android_log_print(ANDROID_LOG_ERROR,"JNI","數組的值:%d",tmp);
        *(javaArray+k) = tmp+10;
    }
    std::string hello = "測試數組傳遞";
    return env->NewStringUTF(hello.c_str());
}

以上 的代碼僅僅是對數組的內容進行輸出。

修改一個數組很簡單,只需要通過指針,很容易做到,代碼如下

可以看到,只需要增加紅框部分就可以做到修改數組。

那麼我們先運行看一下,看是否java層的數組,數據是否改變。

爲了便於觀察,在java層將數組打印出來

現在就開始運行

你會發現一個奇怪的現象,我不是在JNI層修改了嗎?爲什麼還是沒有改變。

原因是這樣的,

*(javaArray+k)指向的數組地址,和 java層所在的數組地址並不是同一個,*(javaArrray+k)裏保存的數據,僅僅是java層數組的一個備份而已。所以無論你怎麼改,肯定是影響不了java層的數組的。那我非要通過JNI函數改變java層的數組,要如何做呢?可以通過如下方式。

你只需要通過ReleaseIntArrayElements這個函數,就可以做到將JNI層的更改,影響到java層。這個函數內部其實就是,將JNI層做的更改,再次拷貝到Java層的數組裏。

ReleaseIntArrayElements的最後一個參數是工作模式,有三種

 0:  刷新java數組 並 釋放c/c++數組
 1 = JNI_COMMIT:
      只刷新java數組
 2 = JNI_ABORT
      只釋放

我們這裏選擇的是0,它會釋放JNI層的備份數組,同時會將JNI層對數組做的更改,進行同步。

明白了這點之後,現在就來運行下吧

可以發現,數據確實更改了。

Android JNI學習07-AndroidStudio3.6 JNI函數調用java層實體類get,set 和 靜態方法,以及獲取和修改成員屬性

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章