【发布时间】:2021-11-04 08:44:07
【问题描述】:
我已在头文件 (Environment.h) 中声明了以下类,并且我想将超类 FieldAccessor 设为抽象:
#include <jni.h>
class FieldAccessor {
public:
FieldAccessor(
JNIEnv* env
) {
this->jNIEnv = env;
}
virtual jobject getValue(jobject, jobject) = 0;
protected:
JNIEnv* jNIEnv;
};
template<typename Type>
class PrimitiveFieldAccessor : public FieldAccessor {
public :
PrimitiveFieldAccessor (
JNIEnv* env, const char name[], const char ctorSig[],
Type (JNIEnv::*getFieldValueFunction) (jobject, jfieldID)
);
jobject getValue(jobject, jobject);
private:
jclass type;
jmethodID constructorId;
Type (JNIEnv::*getFieldValueFunction) (jobject, jfieldID);
};
但我得到以下编译错误:
F:/Shared/Workspaces/Projects/JNI/src/DriverFunctionSupplierNative.cpp: In instantiation of '_jobject* PrimitiveFieldAccessor<Type>::getValue(jobject, jobject) [with Type = long int; jobject = _jobject*]':
F:/Shared/Workspaces/Projects/JNI/src/Environment.h:73:11: required from here
F:/Shared/Workspaces/Projects/JNI/src/DriverFunctionSupplierNative.cpp:80:2: error: must use '.*' or '->*' to call pointer-to-member function in '((PrimitiveFieldAccessor<long int>*)this)->PrimitiveFieldAccessor<long int>::getFieldValueFunction (...)', e.g. '(... ->* ((PrimitiveFieldAccessor<long int>*)this)->PrimitiveFieldAccessor<long int>::getFieldValueFunction) (...)'
这是一段实现文件(DriverFunctionSupplierNative.cpp):
template<typename Type>
PrimitiveFieldAccessor<Type>::PrimitiveFieldAccessor (
JNIEnv* env,
const char name[],
const char ctorSig[],
Type (JNIEnv::*getFieldValueFunction) (jobject, jfieldID)
) : FieldAccessor(env) {
this->jNIEnv = env;
this->type = (jclass)jNIEnv->NewGlobalRef(env->FindClass(name));
this->constructorId = jNIEnv->GetMethodID(this->type, "<init>", ctorSig);
this->getFieldValueFunction = getFieldValueFunction;
}
template<typename Type>
jobject PrimitiveFieldAccessor<Type>::getValue(jobject target, jobject field) {
jfieldID fieldId = jNIEnv->FromReflectedField(field);
return jNIEnv->NewObject(
this->type,
this->constructorId,
this->getFieldValueFunction(target, fieldId)
);
}
【问题讨论】:
-
它不适用于六个字段和方法?你先试一试怎么样。重点是,创建minimal reproducible example 有助于理解问题,这也是需要它的原因。作为这里比较新的用户,也请收下tour阅读How to Ask。
-
所有 4 个声明为 virtual 的方法的错误都是相同的:如果我删除了 virtual 关键字和方法末尾的表达式 '= 0' 我没有编译错误,但是我修改它
-
我减少了代码。而且错误很可能出在方法
jobject PrimitiveFieldAccessor<Type>::getValue(jobject target, jobject field)正是在这行代码中:this->getFieldValueFunction(target, fieldId)但是我还没明白哪个是正确的代码 -
stackoverflow.com/search?q=error%3A+must+use+%27.*%27+or+%27-%3E*%27+to+call+pointer-to-member+function -- 只搜索错误。顺便说一句:它仍然不是minimal reproducible example。
-
您是否尝试将其复制并粘贴到文件中以重现该问题?您可能会发现它并不那么容易,因为它并不完整。例如,对 JNI 的依赖可能仍然是不必要的。
标签: c++ templates abstract-class virtual