2012-04-01 27 views
1

什麼是SWIG等同於存儲一個任意python對象的副本?SWIG相當於存儲一個boost :: python :: object

我很確定我在問什麼是可能的,因爲它可以與boost :: python一起工作(見下文),但是我看不到使用SWIG來做到這一點的方法。

#include <boost/python.hpp> 

using namespace boost::python; 

class MyClass 
{ 
public: 
    // other operations 
    object get_info() { return info_; } 
    void set_info(object info) { info_ = info; } 

private: 
    object info_; 
}; 

BOOST_PYTHON_MODULE(mymodule) 
{ 
    class_<MyClass>("MyClass") 
     .def("get_info", &MyClass::get_info) 
     .def("set_info", &MyClass::set_info) 
    ; 
} 

回答

1

最簡單的例子是:

%module test 

%inline %{ 
class MyClass 
{ 
public: 
    // other operations 
    PyObject *get_info() { return info_; } 
    void set_info(PyObject *info) { info_ = info; } 

private: 
    PyObject *info_; 
}; 
%} 

例如爲:

 
swig -python -Wall -c++ test.i 
g++ -Wall -Wextra test_wrap.cxx -I/usr/include/python2.6 -o _test.so -shared 
python 
Python 2.6.6 (r266:84292, Dec 27 2010, 00:02:40) 
[GCC 4.4.5] on linux2 
Type "help", "copyright", "credits" or "license" for more information. 
>>> import test 
>>> foo = test.MyClass() 
>>> str = "hi" 
>>> foo.set_info(str) 
>>> print foo.get_info() 
hi 
>>> 

但請注意,在這種情況下,標的物的所有權沒有發生變化。如果我完成了foo.set_info("hi"),那麼它將被釋放,因爲在它被稱爲foo.get_info()的時候沒有保留引用。

您可以修復,它通過添加調用:

Py_INCREF(info); 

set_info(),但隨後你需要一個相應的DECREF在析構函數,或者如果set_info()當提及已持有被調用,或爲複製建設或分配。 (或者一些很好的RAII類型可以爲你做所有這些......)

+0

因此,如果這個類是不可複製的,那麼一個簡單的INCREF/DEFREF就足夠了?我不必擔心任何其他特殊情況? – 2012-04-02 00:06:28

+0

@AndrewWalker - 取決於你在想什麼天真。如果你已經設置了一個集合,你需要DECREF。當你摧毀時你也需要DECREF。我真的建議去RAII的方法 - 很難讓它錯誤。 – Flexo 2012-04-02 00:20:38