C++ allows the use of multiple inheritance, where one class can have more than
one base class. Remember back to the 
Transaction, 
Lodgement
and 
Withdrawal classes that we discussed previously. If we wished to
create a 
FundsTransfer class, it would have properties of both a

Lodgement and a 
Withdrawal. So the following structure
could be devised, as in Figure 3.16, “Multiple Inheritance with the 
FundTransfer class.”.
This is a valid structure as a 
Lodgement IS A 
Transaction, a

Withdrawal IS A 
Transaction and at different times
during execution a 
FundTransfer IS A 
Lodgement and
a 
Withdrawal.
Two separate 
Transaction objects are being created, and they do not
interfere with each other (they have their own state).
When using these 
Transaction objects you must be careful to resolve the ambiguity
that results from having two objects of the same class. Suppose, a method was written in the

FundTransfer class to calculate the time taken for the physical cash
transfer to take place (the time between the withdrawal and the lodgement), you could use a code segment
like:
class FundTransfer: public Lodgement,
public Withdrawal
{
private:
// states..
public:
virtual int getTimeTaken()
{
return ( Lodgement::timeOfTransaction -
Withdrawal::timeOfTransaction );
}
};
In this segment of code the multiple parents are comma separated and the 
getTimeTaken()
returns the time taken as an int (could be milliseconds). In this method, the ambiguity
is resolved between the two 
timeOfTransaction states that are inherited by the

FundTransfer class, by specifying the parent that resulted in the inheritance of
that state. So, 
Lodgement::timeOfTransaction is the 
timeOfTransaction
state inherited through the 
Lodgement parent.
A common base class may not be inherited twice!
This same notation may be used to resolve ambiguity when referring to the class directly. If the

Transaction had a 
display() method, and it was to be
called directly, we could use:
FundTransfer *fundPtr; fundPtr -> display(); // not allowed - ambiguous fundPtr -> Lodgement::display(); // OK! fundPtr -> Withdrawal::display(); // OK!
This is awkward and does not give us an appropriate level of abstraction. It would be more appropriate to
declare a new 
display() method in the 
FundTransfer class
to avoid this ambiguity.
In the previous example it made sense to have two individual 
Transaction
objects, each with its own state, otherwise it would not have been possible to calculate the time
taken. This is not always the case. For example:
If the task was to create a special Current Account that had all the
benefits of a 
Deposit account and all the benefits of a 
Current
account, then a structure as shown in Figure 3.17, “Multiple Inheritance with the 
CashSave class.” could be devised. We could
call this class 
CashSave (nothing to do with AIB at all! ;-)).
Since 
Account contains the 
balance state,
and 
CashSave is a type of

Account, we do not want the 
balance state to be
duplicated - having two different 
balance states! To fix this the

CashSave class should only have one instance of its common indirect
base class. This can be achieved by declaring the base class to be virtual.
class Current: public virtual Account
{
// etc..
};
class Deposit: public virtual Account {
// etc..
};
class CashSave: public virtual Current,
public virtual Deposit{
// etc.. virtual is not required here!
};
In effect, we are declaring that if either the 
Current class
or the 
Deposit class should be used in a multiple inheritance hierarchy, then
they should share the same instance of
the 
Account class with any other class that has virtual inheritance of

Account.
So, this simple alteration to the parent results in a shared parent object. The only difficulty with this
design is that the alteration must be made when the 
Current and 
Deposit
classes are being designed. The programmer/designer must therefore be aware of child classes that are to be created
in the future. This is not always possible as the marketing department may not have concieved of a "Cashsave" account
until many years after the original design.
Now that we have an example of a virtual base class, remember to use a dynamic_cast in this
case.
© 2006
Dr. Derek Molloy
(DCU).