在JNI jobject中存储一个c++对象实例,稍后检索
Store a c++ object instance inside JNI jobject and retrieve later
我有一个JNI类,方法是init()
、work()
和cleanup()
。在c++方面,我在init()
期间创建了一个c++类Foo
的实例,然后在work()
期间对其调用一些方法,最后在cleanup()
中删除它。现在我将Foo
的实例存储为c++上的全局单例,以便我可以从不同的JNI调用中检索它。我真正想做的是在传递给每个JNI调用的jobject
实例中存储一个指向Foo
实例的指针,这样我就可以避免拥有全局单例,也可以支持Foo
的多个实例。这样的事情可能发生吗?
可以将指向c++对象的指针存储为Java类成员。例如,在Java中:
class Foo
{
public long ptr = 0;
public native void init();
public native void work();
public native void cleanup();
}
在c++中:
jfieldID getPtrFieldId(JNIEnv * env, jobject obj)
{
static jfieldID ptrFieldId = 0;
if (!ptrFieldId)
{
jclass c = env->GetObjectClass(obj);
ptrFieldId = env->GetFieldID(c, "ptr", "J");
env->DeleteLocalRef(c);
}
return ptrFieldId;
}
class Foo
{
/* ... */
};
extern "C"
{
void Java_Foo_init(JNIEnv * env, jobject obj)
{
env->SetLongField(obj, getPtrFieldId(env, obj), (jlong) new Foo);
}
void Java_Foo_work(JNIEnv * env, jobject obj)
{
Foo * foo = (Foo *) env->GetLongField(obj, getPtrFieldId(env, obj));
foo->work();
}
void Java_Foo_cleanup(JNIEnv * env, jobject obj)
{
Foo * foo = (Foo *) env->GetLongField(obj, getPtrFieldId(env, obj));
delete foo;
}
}
当然。
在JNI中创建Foo实例。只需将指针(指向创建的实例)作为jlong类型返回即可。因此您可以稍后将其用作处理程序。下面是一个例子:
JNIEXPORT jlong JNICALL Java_com_example_init(JNIEnv *env, jobject thiz) {
Foo* pFoo = new Foo();
if (NULL == pFoo) {
// error handling
}
pFoo->initialize();
return reinterpret_cast<jlong>(pFoo);
}
JNIEXPORT void JNICALL Java_example_start(JNIEnv *env, jobject thiz,
jlong fooHandle) {
Foo* pFoo = reinterpret_cast<Foo*>(fooHandle);
pFoo->start();
}
您可以在java中使用long来完成此操作,但是我认为在预计在沙盒中操作的语言的实例变量中放置指向某些本机内存地址的指针并不是一个好主意。它很草率,可能是一个利用向量,这取决于你做什么。
我猜你正在遇到这个问题,因为你的本机代码非常接近你的JNI代码。如果您将JNI层构建为本机代码和Java之间的转换,您可能会发现使用它更容易。
相关文章:
- 对象实例化调用构造函数的次数太多
- C++ 中的基本单一实例对象
- 在 C++ 中,类实例对象 do memcpy 总是崩溃
- C++:在函数中使用当前实例(对象)
- 单一实例对象是否通过线程安全返回shared_ptr
- std::system 实例化单一实例对象时的异常
- 使用unique_ptr的单一实例对象
- 如果已创建 mongocxx::实例对象,则无法创建该对象
- 单一实例对象的未解决外部符号链接错误
- 实例对象如何查看函数的对象参数的私有成员?
- 在C++中调用单一实例对象的正确方法
- 声明模板化实例对象的函数指针
- 如何在"boost::function"中访问类实例(对象)指针?
- 删除单一实例对象 cpp 时出现内存泄漏
- 从 EXE 和 DLL 访问单一实例对象中的成员变量
- 如何在 C++11 中将 vector 与引用类型实例对象一起使用
- 为什么在构造函数退出时创建新的实例(对象)
- "类实例对象"未在此范围内声明
- c++实例对象的函数指针
- 如何正确存储多个实例对象