JNI C++ 调用Java 返回字符串以及jstring转成字符串(二)

C++ 调用Java方法基本使用请参考:

https://blog.csdn.net/u011905195/article/details/112393826

一、定义Java 方法:

 

public String testString(){
 
    return "C++调用Java testString";
}

public static String testStaticString(){
 
    return "C++调用Java testStaticString";
}

二、 C++进行调用

void testString(JNIEnv *env,jobject thiz){
    //获取java对象类
    jclass jclazz = env->GetObjectClass(thiz);
    /**
     * 获取java对象方法ID
     * clazz:对象类
     * name:方法名
     * sig:方法签名
     */
    jmethodID jmethodID = env->GetMethodID(jclazz, "testString",
                                           "()Ljava/lang/String;");
    /**
     * obj:参数是对象
     * methodID: 方法名ID
     * ... :动态参数(有几个就传几个对应类型的参数)
     */
    jstring result = (jstring) env->CallObjectMethod(thiz, jmethodID);
    LOGD("JniNative返回数据:%s",jstring2string(env,result).c_str());
}

void testStaticString(JNIEnv *env,jobject thiz){
    //获取java对象类
    jclass jclazz = env->GetObjectClass(thiz);
    /**
     * 获取java对象方法ID
     * clazz:对象类
     * name:方法名
     * sig:方法签名
     */
    jmethodID jmethodID = env->GetStaticMethodID(jclazz, "testStaticString",
                                                 "()Ljava/lang/String;");
    /**
     * clazz:参数是类
     * methodID: 方法名ID
     * ... :动态参数(有几个就传几个对应类型的参数)
     */
    jstring result = (jstring) env->CallStaticObjectMethod(jclazz, jmethodID);
    LOGD("JniNative返回数据:%s",jstring2string(env,result).c_str());
}

三、把获取到的jstring 转成 字符串

string jstring2string(JNIEnv *env, jstring jStr) {
    if (!jStr)
        return "";

    const jclass stringClass = env->GetObjectClass(jStr);
    const jmethodID getBytes = env->GetMethodID(stringClass, "getBytes", "(Ljava/lang/String;)[B");
    const jbyteArray stringJbytes = (jbyteArray) env->CallObjectMethod(jStr, getBytes, env->NewStringUTF("UTF-8"));

    size_t length = (size_t) env->GetArrayLength(stringJbytes);
    jbyte* pBytes = env->GetByteArrayElements(stringJbytes, NULL);

    std::string ret = std::string((char *)pBytes, length);
    env->ReleaseByteArrayElements(stringJbytes, pBytes, JNI_ABORT);

    env->DeleteLocalRef(stringJbytes);
    env->DeleteLocalRef(stringClass);
    return ret;
}

 

四、主要的代码

Java部分

 

package com.example.jnidemo;

import android.util.Log;

public class JniNative {
    private static final String TAG = "JniNative";
    // Used to load the 'native-lib' library on application startup.

    static {
        System.loadLibrary("native-lib");
    }
    /**
     * A native method that is implemented by the 'native-lib' native library,
     * which is packaged with this application.
     */
    public native String stringFromJNI();

    public void testVoid(){
        Log.e(TAG,"C++调用Java testVoid");
    }

    public static void testStaticVoid(){
        Log.e(TAG,"C++调用Java testStaticVoid");
    }

    public int testInt(){
        Log.e(TAG,"C++调用Java testInt");
        return 0;
    }

    public static int testStaticInt(){
        Log.e(TAG,"C++调用Java testStaticInt");
        return 0;
    }

    public String testString(){
        Log.e(TAG,"C++调用Java testString");
        return "C++调用Java testString";
    }

    public static String testStaticString(){
        Log.e(TAG,"C++调用Java testStaticString");
        return "C++调用Java testStaticString";
    }

}

C ++部分:

#include <jni.h>
#include <string>
#include "common/logjni.h"
using namespace std;

void testVoid(JNIEnv *env,jobject thiz);
static void testStaticVoid(JNIEnv *env,jobject thiz);
void testInt(JNIEnv *env,jobject thiz);
static void testStaticInt(JNIEnv *env,jobject thiz);
void testString(JNIEnv *env,jobject thiz);
void testStaticString(JNIEnv *env,jobject thiz);
string jstring2string(JNIEnv *env, jstring jStr);
extern "C"
JNIEXPORT jstring JNICALL
Java_com_example_jnidemo_JniNative_stringFromJNI(JNIEnv *env, jobject thiz) {
    // TODO: implement stringFromJNI()
    std::string hello = "Hello from C++";
    testVoid(env,thiz);
    testStaticVoid(env,thiz);
    testInt(env,thiz);
    testStaticInt(env,thiz);
    testString(env,thiz);
    testStaticString(env,thiz);
    return env->NewStringUTF(hello.c_str());
}

void testVoid(JNIEnv *env,jobject thiz){
    //获取java对象类
    jclass jclazz = env->GetObjectClass(thiz);
    /**
     * 获取java对象方法ID
     * clazz:对象类
     * name:方法名
     * sig:方法签名
     */
    jmethodID jmethodID = env->GetMethodID(jclazz, "testVoid",
                                           "()V");
    /**
     * obj:参数是对象
     * methodID: 方法名ID
     * ... :动态参数(有几个就传几个对应类型的参数)
     */
    env->CallVoidMethod(thiz, jmethodID);
}

static void testStaticVoid(JNIEnv *env,jobject thiz){
    //获取java对象类
    jclass jclazz = env->GetObjectClass(thiz);
    /**
     * 获取java对象方法ID
     * clazz:对象类
     * name:方法名
     * sig:方法签名
     */
    jmethodID jmethodID = env->GetStaticMethodID(jclazz, "testStaticVoid",
                                           "()V");
    /**
     * clazz:参数是类
     * methodID: 方法名ID
     * ... :动态参数(有几个就传几个对应类型的参数)
     */
    env->CallStaticVoidMethod(jclazz, jmethodID);
}

void testInt(JNIEnv *env,jobject thiz){
    //获取java对象类
    jclass jclazz = env->GetObjectClass(thiz);
    /**
     * 获取java对象方法ID
     * clazz:对象类
     * name:方法名
     * sig:方法签名
     */
    jmethodID jmethodID = env->GetMethodID(jclazz, "testInt",
                                           "()I");
    /**
     * obj:参数是对象
     * methodID: 方法名ID
     * ... :动态参数(有几个就传几个对应类型的参数)
     */
    env->CallIntMethod(thiz, jmethodID);
}

static void testStaticInt(JNIEnv *env,jobject thiz){
    //获取java对象类
    jclass jclazz = env->GetObjectClass(thiz);
    /**
     * 获取java对象方法ID
     * clazz:对象类
     * name:方法名
     * sig:方法签名
     */
    jmethodID jmethodID = env->GetStaticMethodID(jclazz, "testStaticInt",
                                                 "()I");
    /**
     * clazz:参数是类
     * methodID: 方法名ID
     * ... :动态参数(有几个就传几个对应类型的参数)
     */
    env->CallStaticIntMethod(jclazz, jmethodID);
}

void testString(JNIEnv *env,jobject thiz){
    //获取java对象类
    jclass jclazz = env->GetObjectClass(thiz);
    /**
     * 获取java对象方法ID
     * clazz:对象类
     * name:方法名
     * sig:方法签名
     */
    jmethodID jmethodID = env->GetMethodID(jclazz, "testString",
                                           "()Ljava/lang/String;");
    /**
     * obj:参数是对象
     * methodID: 方法名ID
     * ... :动态参数(有几个就传几个对应类型的参数)
     */
    jstring result = (jstring) env->CallObjectMethod(thiz, jmethodID);
    LOGD("JniNative返回数据:%s",jstring2string(env,result).c_str());
}

void testStaticString(JNIEnv *env,jobject thiz){
    //获取java对象类
    jclass jclazz = env->GetObjectClass(thiz);
    /**
     * 获取java对象方法ID
     * clazz:对象类
     * name:方法名
     * sig:方法签名
     */
    jmethodID jmethodID = env->GetStaticMethodID(jclazz, "testStaticString",
                                                 "()Ljava/lang/String;");
    /**
     * clazz:参数是类
     * methodID: 方法名ID
     * ... :动态参数(有几个就传几个对应类型的参数)
     */
    jstring result = (jstring) env->CallStaticObjectMethod(jclazz, jmethodID);
    LOGD("JniNative返回数据:%s",jstring2string(env,result).c_str());
}

string jstring2string(JNIEnv *env, jstring jStr) {
    if (!jStr)
        return "";

    const jclass stringClass = env->GetObjectClass(jStr);
    const jmethodID getBytes = env->GetMethodID(stringClass, "getBytes", "(Ljava/lang/String;)[B");
    const jbyteArray stringJbytes = (jbyteArray) env->CallObjectMethod(jStr, getBytes, env->NewStringUTF("UTF-8"));

    size_t length = (size_t) env->GetArrayLength(stringJbytes);
    jbyte* pBytes = env->GetByteArrayElements(stringJbytes, NULL);

    std::string ret = std::string((char *)pBytes, length);
    env->ReleaseByteArrayElements(stringJbytes, pBytes, JNI_ABORT);

    env->DeleteLocalRef(stringJbytes);
    env->DeleteLocalRef(stringClass);
    return ret;
}
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值