Hello pythonians! ;-D , I have a little problem when I expose (assisted by boost.python) classes with virtual functions, specially with operator(). In the C++ code below I test two different implementations of a member function of A that takes as an argument the abstract class Base (see Option 1 / Option 2): - Both compile without problems - Only the second works in python (see python program below).
It seems like if the problem is in the way I expose operator()... but I do not understand it very well Any clue about why this is happening?I would appreciate any comment on this. Thank you very much in advance. :-D Pedro. //....................................................... //................ C++ code...................... //....................................................... #include <boost/python.hpp> #define OPTION1 //#undef OPTION1 struct Base { virtual ~Base() {} virtual int f() = 0; // Like in Boost.python tutorial virtual int g(int) = 0; // With 1 argument virtual bool operator()(int ii) =0; // __call__ - type function }; class A{ private: int v_; public: A(int v): v_(v){} #ifdef OPTION1 /* Option 1 */ int fun(Base& c) const { return c(v_)?(c.g(v_)+c.f()):33; } #else /* Option 2 */ int fun(Base& c) const { return (c.g(v_)+c.f()); } #endif }; //:::::::::::::::::::::::::::BOOST::PYTHON in action::::::::::::::::::::::::::: using namespace boost::python; struct BaseWrap : Base, wrapper<Base> { int f(){return call<int>(this->get_override("f").ptr());} int g(int ii){return call<int>(this->get_override("g").ptr(),ii);} bool operator()(int ii){ return call<bool>(this->get_override("operator()").ptr(),ii);} }; BOOST_PYTHON_MODULE(test2py) { class_<A>("A",init<int>()) .def("fun",&A::fun); class_<BaseWrap, boost::noncopyable>("Base") .def("f", pure_virtual(&Base::f)) .def("g", pure_virtual(&Base::g)) .def("__call__", pure_virtual(&Base::operator())) ; }; //....................................................... //................ Python code................... //....................................................... from test2py import * ## Extension of C++ class in python class Derived(Base): def f(self): return 44 def g(self,n): return n def __call__(self, v): return (v<23) d=Derived() print d.f() print d.g(3) print "is 20<23 and 24<23", d(20), d(24) a=A(20) print a.fun(d) b=A(24) print b.fun(d) //...................................................................... //................ Executing Python code.................. //..................................................................... With Option 1 IS NOT WORKING!! ... int fun(Base& c) const { return c(v_)?(c.g(v_)+c.f()):33; } ... >>> 44 3 is 20<23 and 24<23 True False Traceback (most recent call last): File "d:\My_Documents\src\pysource\test.py", line 29, in ? print a.fun(d) TypeError: 'NoneType' object is not callable With Option 2 IS WORKING!! ... int fun(Base& c) const { return (c.g(v_)+c.f()); } ... >>> 44 3 is 20<23 and 24<23 True False 64 68 >>> -- http://mail.python.org/mailman/listinfo/python-list