3
我有JNI級別的代碼。它可以拋出異常。代碼是:Java中使用JNI的代碼流程
#include "JavaGlueClass.h"
#include <stdio.h>
#include <windows.h>
#include <string.h>
jint throwNoClassDefError(JNIEnv *env, const char *message)
{
jclass exClass;
char *className = (char *) "java/lang/NoClassDefFoundError" ;
exClass = env->FindClass(className);
if (exClass != NULL) {
return env->ThrowNew(exClass, message);
}
//free the local ref
env->DeleteLocalRef(exClass);
}
void throwGetFieldIDException(JNIEnv *env)
{
const char *className = "GetFieldIDException";
jclass exClass = env->FindClass(className);
if (exClass == NULL) {
throwNoClassDefError(env, className);
} else {
env->ThrowNew(exClass, "GetFieldIDException message");
}
env->DeleteLocalRef(exClass);
printf("printprint");
}
JNIEXPORT jobject JNICALL Java_JavaGlueClass_test(JNIEnv *env, jobject obj)
{
jmethodID constructor;
jobject object;
jclass clazz;
jfieldID fid;
jstring stringField;
clazz = env->FindClass("Information");
if (clazz == 0) {
printf("error while finding class");
throwNoClassDefError(env, "no such class");
} else {
//create object throuht constructor
constructor = env->GetMethodID(clazz, "<init>", "()V");
object = env->NewObject(clazz, constructor);
// set private value1 field
stringField = env->NewStringUTF("str1");
//fid = env->GetFieldID(clazz,"value1","Ljava/lang/String;");
fid = NULL;
if (fid == NULL) {
throwGetFieldIDException(env, "error with value1 field.");
//return NULL;
}
env->SetObjectField(object, fid, stringField);
//set private value2 field
fid = env->GetFieldID(clazz,"value2","I");
if (fid == NULL) {
throwGetFieldIDException(env, "error with value1 field.");
//return NULL;
}
env->SetIntField(object, fid, 1);
// set private value3 field
stringField = env->NewStringUTF("str2");
fid = env->GetFieldID(clazz,"value3","Ljava/lang/String;");
if (fid == NULL) {
throwGetFieldIDException(env, "error with value1 field.");
//return NULL;
}
env->SetObjectField(object, fid, stringField);
//set private value4 field
fid = env->GetFieldID(clazz,"value4","I");
if (fid == NULL) {
throwGetFieldIDException(env, "error with value1 field.");
//return NULL;
}
env->SetIntField(object, fid, 2);
printf("end of cpp function");
return object;
}
}
Java_JavaGlueClass_test函數創建自定義信息類的對象。每次我設置類字段時,都會檢查「fid」是否爲NULL。 我讀了關於那些是未決異常的JNI異常。我發現將拋出的第一個異常會將代碼流移到Java級別(而不是JNI級別)。但是在JNI級別的異常之後的其餘代碼呢?據我瞭解,它將被執行。 第一個異常之後是否有可能拋出第二,第三等異常?我應該在拋出異常之後返回NULL或其他什麼,以便JNI級別的其餘代碼不會被執行?
好的。正如我所看到的,我必須「在異常發生後必須明確實施控制流程」 –
好的。正如我所看到的,「在異常發生後必須明確地實施控制流程」。發生異常後實現其餘代碼的最佳方式是什麼?我是否必須使用if-else序列,如 ' //代碼 if(condition1){ throwsException1Expr(); //什麼都不做 } else { //代碼 if(條件2){ throwsException2Expr(); //什麼也不做 } } ' 或這樣的: ' //代碼 如果(條件1){ throwsException1Expr(); return; } //代碼 if(條件2){ throwsException2Expr(); return; } }' –
沒有最好的方法,選擇最簡單的一個。 – ignis