In C++, is it possible to have a base plus derived class implement a single interface?
For example:
class Interface
{
public:
virtual void BaseFunction() = 0;
virtual void DerivedFunction() = 0;
};
class Base
{
public:
virtual void BaseFunction(){}
};
class Derived : public Base, public Interface
{
public:
void DerivedFunction(){}
};
void main()
{
Derived derived;
}
This fails because Derived can not be instantiated. As far as the compiler is concerned Interface::BaseFunction is never defined.
So far the only solution I've found would be to declare a pass through function in Derived
class Derived : public Base, public Interface
{
public:
void DerivedFunction(){}
void BaseFunction(){ Base::BaseFunction(); }
};
Is there any better solution?
EDIT: If it matters, here is a real world problem I had using MFC dialogs.
I have a dialog class (MyDialog lets say) that derives from CDialog. Due to dependency issues, I need to create an abstract interface (MyDialogInterface). The class that uses MyDialogInterface needs to use the methods specific to MyDialog, but also needs to call CDialog::SetParent. I just solved it by creating MyDialog::SetParent and having it pass through to CDialog::SetParent, but was wondering if there was a better way.
C++ doesn't notice the function inherited from Base already implements BaseFunction
: The function has to be implemented explicitly in a class derived from Interface
. Change it this way:
class Interface
{
public:
virtual void BaseFunction() = 0;
virtual void DerivedFunction() = 0;
};
class Base : public Interface
{
public:
virtual void BaseFunction(){}
};
class Derived : public Base
{
public:
virtual void DerivedFunction(){}
};
int main()
{
Derived derived;
}
If you want to be able to get away with only implementing one of them, split Interface
up into two interfaces:
class DerivedInterface
{
public:
virtual void DerivedFunction() = 0;
};
class BaseInterface
{
public:
virtual void BaseFunction() = 0;
};
class Base : public BaseInterface
{
public:
virtual void BaseFunction(){}
};
class Derived : public DerivedInterface
{
public:
virtual void DerivedFunction(){}
};
class Both : public DerivedInterface, public Base {
public:
virtual void DerivedFunction(){}
};
int main()
{
Derived derived;
Base base;
Both both;
}
Note: main must return int
Note: it's good practise to keep virtual
in front of member functions in the derived that were virtual in the base, even if it's not strictly required.
It looks like it's not quite the case that Derived "is-a" Base, which suggests that containment may be a better implementation than inheritance.
Also, your Derived member functions should be decalred as virtual as well.
class Contained
{
public:
void containedFunction() {}
};
class Derived
{
public:
virtual void derivedFunction() {}
virtual void containedFunction() {return contained.containedFunction();}
private:
Containted contained;
};
You can make the contained member a reference or smart pointer if you want to hide the implementation details.
The problem is that with your example, you have two implementations of Interface
, the one coming from Base
and the one coming from Derived
. This is by design in the C++ language. As already pointed out, just remove the Interface
base class on the definition of Derived
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With