java – 在JNI中,是否有比jlong​​更便携的方法来封装指针?

我已经看到使用long / jlong​​来允许 Java对象保持C指针的示例:
class Foo {
    private native long create();
}

struct Foo { };

JNIEXPORT jlong JNICALL Java_Foo_create
  (jnienv *,jobject)
{
    return (jlong) (new Foo);
}

这让我觉得有点紧张,因为它假设一个指针适合64位;这在OS / 400上是不真实的.

是否有更安全的解决方案,例如封装C指针的Java标准库类?

解决方法

您可以使用哈希表来存储指针并将此哈希表的键返回给用户.喜欢:
std::unordered_map<long,Foo*> handles;
 long newHandle = 0
 ...
  JNIEXPORT jlong JNICALL Java_Foo_create
  (jnienv *,jobject)
   {
       Foo* ptr = new Foo;
       long handle = newHandle;
       handles.insert(std::pair<long,Foo*>(newHandle++,ptr));
       return handle;
   }

现在您可以使用句柄从hashmap获取指针:

JNIEXPORT void JNICALL Java_Foo_use
  (jnienv *,jobject,jlong handle) {
   auto iter = handles.find(handle);
   if (iter != handles.end()) {
       Foo* ptr = iter->second;
       // use Foo* here
   }
}

方法还可以帮助您检查对象是否已被删除删除仍然存在的所有Foo对象.
缺点是访问hashmap以获取指针会降低性能.此外,您应该使用多线程访问或使用线程安全映射实现来保护您的句柄映射.

或者,如果您需要为Java实现包装器,我建议考虑SWIG(Simplified Wrapper和Interface Generator).

相关文章

最近看了一下学习资料,感觉进制转换其实还是挺有意思的,尤...
/*HashSet 基本操作 * --set:元素是无序的,存入和取出顺序不...
/*list 基本操作 * * List a=new List(); * 增 * a.add(inde...
/* * 内部类 * */ 1 class OutClass{ 2 //定义外部类的成员变...
集合的操作Iterator、Collection、Set和HashSet关系Iterator...
接口中常量的修饰关键字:public,static,final(常量)函数...