我将尽我的意图,因为可能有不止一种方法。首先,我有一个抽象基类FooBase和一个虚函数SayHi()Foo1是许多派生类之一。

class FooBase {
public:
    virtual void SayHi() = 0;
};

class Foo1 : public FooBase {
public:
    virtual void SayHi() {
        std::cout<<"Foo1 says Hi\n";
    }
};

我也有一个Component类,有时我想将Foo..类实现为Components。我使用了模板类,以便FooBase的任何子类都可以具有Component包装器。
class FooComponentBase : public Component {
public:
    virtual FooBase& GetFoo() = 0;
};

template <class T>
class FooComponent : public FooComponentBase {
private:
    T m_foo;
public:
    virtual FooBase& GetFoo() {return m_foo;}
};

现在,FooComponentBase是包含FooBase的任何子类的组件的接口(interface):
void DoTest() {
    FooComponentBase* pFooComponent = new FooComponent<Foo1>;
    pFooComponent->GetFoo().SayHi();                            // "Foo1 says Hi"
    delete pFooComponent;
}

到目前为止,一切正常。但是,如果FooComponent是从FooBase继承的,则可能会更整洁,因此我们不需要遍历GetFoo()即可访问FooBase的方法。
// Inherited version

class FooComponentBase : public Component {};

template <class T>
class FooComponent : public FooComponentBase, public T {};

不幸的是,即使FooComponentBase的所有派生类都可以访问FooBase
void DoTest() {
    FooComponentBase* pFooComponent = new FooComponent<Foo1>;
    pFooComponent->SayHi();     // Error, FooComponentBase has no SayHi() function
    delete pFooComponent;
}

我找不到使这项工作可行的方法。似乎应该有一种方法,也许可以使用虚拟继承。
class FooComponentBase : public Component, virtual public FooBase {};

但这也不会编译,因为我们无法实例化抽象类。我希望我的意图很明确,我想使FooComponentBase为抽象基类,例如FooBase但具有Component继承,因此我可以使用它来访问每种FooComponent
有没有一种整洁的方式做到这一点?

最佳答案

如果在一个地方使用虚拟继承,那么如果要使用相同的基本实现,则必须在各处使用它:

class Foo1 : public virtual FooBase {

另一种方式(虽然不太好但是可能对您有用)是在FooBase中实现FooComponent的所有功能:
class FooComponentBase : public Component, public FooBase {
};

template <class T>
class FooComponent : public FooComponentBase {
private:
    T m_foo;
public:
    void SayHi() {m_foo.SayHi();}
};

甚至:
class FooComponentBase : public Component, public FooBase {
};

template <class T>
class FooComponent : public FooComponentBase, public T {
public:
    void SayHi() {T::SayHi();}
};

08-06 15:39