如何从基类派生私有地继承,但实现基类的公共接口?

时间:2017-12-05 12:18:05

标签: c++ inheritance encapsulation

假设库中有两个不可更改的类,AB,就像这里一样:

class A
{
public:
    virtual void doCustomThings() = 0;
    virtual void doOtherThings() = 0;
    void doSomething();
private:
    SomeType1 someData;
};

class B : public A
{
public:
    void doCustomThings() override;
    void doOtherThings() override;
    void someUsefulUtility();
private:
    SomeType2 otherData;
};

我正在尝试根据A中提供的某些内容实现B的界面,所以我这样做:

class C : public B
{
public:
    void doCustomThings() override; // uses B::someUsefulUtility()
    // leave B::doOtherThings() not overridden
private:
    SomeType3 myData;
};

但我不打算C B,即我不希望C的引用可隐式转换为{{1}虽然它应该可以转换为B&

首先想到的是使用虚拟继承,然后继承A&。但我的案例中的public A, private BA类不可编辑,要在此处使用虚拟继承,我需要B继承为class B

另一个想法是考虑组合而不是继承。但是,如果我从public virtual A派生并且A作为私人成员,我将无用地B两次,这看起来不够优雅。

有没有像A::someData这样的好方法,所以在给定上述约束的情况下,只有一个基类class C : public A, private B

2 个答案:

答案 0 :(得分:0)

是的,使用私有继承并使用using公开所需的成员。

class C : private B
{
public:
    using B::A;// to make it convertible to A
    using B::doOtherThings;

    void doCustomThings() override {
        std::cout<<"C::doCustomThings()\n";    
    }
private:
    char myData;
};

Working example

答案 1 :(得分:-1)

是的,仅使用A的继承,使用B的合成,并委托给B成员(不是基础)

class C : public A
{
public:
    void doOtherThings() override { myB.doOtherThings(); }

    void doCustomThings() override {
        std::cout<<"C::doCustomThings()\n";    
    }
private:
    B myB;
    SomeType3 myData;
};