There is the general recomendation that multiple inheritance is to be avoided. However, I think it is worthwhile to understand multiple inheritance and its consequences. Especially when using abstract base classes as interfaces, inheriting (implementing) multiple interfaces can make a lot of sense. If multiple inheritance is really needed be aware of some problems that might come up.
Sometimes multiple inheritance is used where the object-oriented concept composition should be used. This mistake is ususally a misunderstanding of the concept of inheritance. Inheritance creates a is-a relationship between to classes. The derived class is a specialization of the class it inherits from. For example, a car is a vehicle. However, sometimes inheritance is misused to create a has-a relationship. In such cases composition is the more accurate relationship. For example, a car has an engine; the class car is not a specialization of the class engine, or the other way around, the class engine is not an abstraction of the class car.
Consider the following example program. Here a class
C inherits from classes
B have exactly the same method
foo(). Note that the two methods have different definitions.
This program will not compile because the compiler does not know which of the two
foo() methods to use.
With a little modification we can help the compiler to choose a method:
The diamond problem
The diamond problem occurs when two superclasses
C of a class
D derive from the same base class
A. In this case
D gets two copies of all attributes in
A. This structure causes ambiguity and very likely unintended behaviour too. Namely, the constructor and destructor of class
A will be called twice.
Here is the code for the depicted scenario:
The output of this program is:
Virtual inheritance for the rescue
Depending on the actual class this is just a waste of resources or a more severe problem. The duplicate call to the constructor of class
A might acquire limited resources or it might open a network connection. Furthermore, the destructor of class A might free something twice which could be problematic.
There is an easy way to solve the problem of duplication: virtual inheritance. By using the keyword
virtual for the inheritance of classes
With this modification the output changes to: