[C++-sig] can these exports be avoided

Gennadiy Rozental rogeeff at gmail.com
Mon Nov 10 08:56:14 CET 2008


Simple scenario:

class IObject {};

class Base : public IObject {
public:
   virtual void foo() {}
};

class Derived : public Base {
   virtual void foo() {}
};

Both IObject and Base are exported into Python:

bp::class_<IObject,noncopyable>( "IObject", bp::no_init );

bp::class_<Base,bp::bases<IObject>,noncopyable>( "Base", bp::no_init )
   .def( "foo", &Base::foo );

Also imagine I've got function like this:

IObjectPtr
create( std::string const& class_name )
{
...
  if(class_name=="Derived")
     return IObjectPtr(new Derived);
}

and this function is also exported into Python.

Now in Python I've got code like this:

o = mymodule.create( "Derived" );
print type(o)

As it stands above print statement produces "mymodule.IObject". What would be
preferable if it can produce mymodule.Base, so I can invoke method foo.

It can be resolved with additional export for class Derived:

bp::class_<Derived,bp::bases<Base>,noncopyable>( "Derived", bp::no_init );

In which case above print statement starts to show mymodule.Derived. But I would
really prefer to avoid these exports for derived classes. After all RTTI
information should shoe Boost.Python whole hierarchy, isn't it? Why can't it
figure out that pointer produced by create actually convertible to Base*, even
though it knows nothing about Derived?

Does any one have any workarounds?

Thanks,

Gennadiy




More information about the Cplusplus-sig mailing list