Boost.Python package hierarchies avoiding diamond inheritance

I am having trouble finding the best way to wrap a series of classes with Boost.Python while avoiding the messy inheritance issues. Let's say I have classes A, B and C with the following structure:

struct A {
    virtual void foo();
    virtual void bar();
    virtual void baz();
};

struct B : public A {
    virtual void quux();
};

struct C : public A {
    virtual void foobar();
};

      

I want to wrap all classes A, B and C so that they can be extended from Python. The usual way to achieve this would be as follows:

struct A_Wrapper : public A, boost::python::wrapper<A> {
    //dispatch logic for virtual functions
};

      

Now, for classes B and C that extend from A, I would like to be able to inherit and exchange the wrapping implementation for A. So I would like to do something along the lines of:

struct B_Wrapper : public B, public A_Wrapper, public boost::python::wrapper<B> {
    //dispatch logic specific for B
};

struct C_Wrapper : public C, public A_Wrapper, public boost::python::wrapper<C> {
    //dispatch logic specific for C
}

      

However, it looks like this will introduce all sorts of nasty things with double inheritance of the boost winding base and double inheritance of A in the B_Wrapper and C_Wrapper objects. Is there a general way for this instance to be resolved that I am missing?

thanks.

+2


a source to share


2 answers


One approach is to actually get:

struct B : virtual public A, ... { };
struct C : virtual public A, ... { };
struct A_Wrapper : virtual public A, ... { };

      



Take a look at the C ++ FAQ Lite items for notes and what this implies.

+1


a source


I had exactly the same problem and just didn't inherit B_Wrapper from A_Wrapper (copy and paste was enough for my needs). I think it is possible to propagate a generic implementation in a helper class:

template<class ADERIVED>
struct A_Implem: public ADERIVED, public wrapper<ADERIVED>
{
    // dispatch logic
};

      



And then:

struct A_Wrapper: public A_Implem<A>
{
// ...
};


struct B_Wrapper: public A_Implem<B>
{
// ...
};

      

+1


a source







All Articles