【发布时间】:2010-09-20 16:36:25
【问题描述】:
我正在使用 SWIG 从 Java 访问 C++ 代码。
公开非常量引用传递的 std::string 参数的最简单方法是什么?
感谢 typemaps.i,我将通过引用传递的原语公开为 Java 数组,而 const std::string&s 公开为 java.lang.String,感谢 std_string.i。但是非常量 std::string& 暴露为不透明指针类型SWIGTYPE_p_std__string。
当前:
// C++ method -> // Java wrapper of C++ method
void foo( int & i ) -> public void foo( int[] i ); // OK
void bar( const std::string & s ) -> public void bar( String s ); // OK
void baz( std::string & s ) -> public void baz( SWIGTYPE_p_std__string s ); // :(
期望:
void foo( int & i ) -> public void foo( int[] i ); // OK
void bar( const std::string & s ) -> public void bar( String s ); // OK
void baz( std::string & s ) -> public void baz( String[] s ); // OK
更新:我找到了一个解决方案,如下所述。然而,这花费了比几秒钟更多的努力。我仍然有兴趣了解简单的方法。
【问题讨论】:
-
因为Java String 类是不可变的。因此,即使您传递了一个虚假的 String 数组,您也不能像传递引用所暗示的那样修改它。
-
@Martin York - 字符串对象是不可变的。但是,String 数组的成员是对 String 对象的可变引用。
-
@Andy Thomas-Cramer:但这与通过引用传递不同。您正在传递一个可以操作的对象。但是对于字符串数组,对象仍然是不可更改的。除非您建议被调用的函数可以通过替换来更改字符串!这将需要 Glue 代码获取返回的 Java String 对象并将其放入传递的 C++ 字符串对象中。
-
@Martin York - 我来包装传递引用,而不是实现它。目标是发送和接收数据。原始类型的解决方法是在函数进入之前和函数退出之后转换数组成员。我用 String[] 为 std::string& 寻求同样的方法。在 Java 中,String[] 包含对 String 对象的引用——指针。本机胶水代码可以很容易地用一个对 Java 字符串的新引用替换单例数组成员,该 Java 字符串是从它通过引用传递的本地 std::string 转换而来的。我知道原始的 Java String 对象没有被修改,但我不需要。
-
@Andy Thomas-Cramer:我明白你在做什么。但问题是 int/String 在 Java 中是根本不同的。请注意,int 是未装箱的,而不是对象。