I'm trying to expose my C++ Classes to Python using Boost.Python. Here is a simplyfied version of what i'm trying to do:
I have a class A deriving from boost::noncopyable and a second class B with a method that takes a reference to A as an argument.
class A : boost::noncopyable { /*...*/ };
class B {
public:
virtual void do_something(A& a) {
/*...*/
}
};
I'm exposing the classes as follows:
/* Wrapper for B, so B can be extended in python */
struct BWrap : public B, wrapper<B> {
void do_something(A &a) {
if (override do_something = this->get_override("do_something")) {
do_something(a);
return;
}
else {
B::do_something(a);
}
}
void default_do_something(A& a) { this->B::do_something(a); }
};
BOOST_PYTHON_MODULE(SomeModule) {
class_<A, boost::noncopyable>("A");
class_<BWrap, boost::noncopyable>("B")
.def("do_something", &B::do_something, &BWrap::default_do_something)
;
}
I extend B in python like this:
test.py:
import SomeModule
class BDerived(SomeModule.B):
def do_something(self, a):
pass
and call the extended B like this:
try {
py::object main = py::import("__main__"); \
py::object global(main.attr("__dict__")); \
py::object result = py::exec_file("test.py", global, global); \
py::object pluginClass = global["BDerived"]; \
py::object plugin_base = pluginClass(); \
B& plugin = py::extract<B&>(plugin_base) BOOST_EXTRACT_WORKAROUND;
A a;
B.do_something(a);
}
catch (py::error_already_set) {
PyErr_Print();
}
However this results in an error message:
TypeError: No to_python (by-value) converter found for C++ type: A
If A
isn't derived from boost::noncopyable
the code runs without any errors but the argument a in do_something(A& a)
gets copied during the function call even though it's passed in by reference. But just removing the noncopyable requirement on A
isn't an option since it's there for a reason.
Any suggestions how to solve the problem?
Thanks.
Change B.do_something(a);
to B.do_something(boost::ref(a));
.
See Calling Python Functions and Methods in the boost manual.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With