条款 40 :明智而省慎地使用多重继承

条款 40 :明智而省慎地使用多重继承

Use multiple inheritance judiciously.

多重继承是C++的一个特色。对于多重继承,C++社群也有两种观点,一种认为多重继承是好的,另一种则认为应不要使用多重继承。

我们来看一段多重继承的代码:

class BorrowableItem{//图书馆允许你借某些东西
    public:
    void checkOut();//离开时进行检查
    ...
};

class ElectronicGadget{
    private:
    bool checkOut()const;//自我检测,成功则返回
};

class MP3Player://注意这里的多重继承
	public BorrowableItem,
	public ElectronicGadget
    {...};//这里定义不是我们关心的重点
MP3Player mp;
mp.checkOut();//这里有歧义,到底该调用哪一个checkOut?

对于上述情况:

C++判别方式与解析重载函数规则一样:找到最佳匹配。(本例中两个函数匹配度下相同,这也是出现起义的原因)。为了解决这个问题你必须指明到底调用哪一个函数,例如BorrowableItem::check().

我们再来看一个多重继承代码:

class File{...};
class InFile:public File{...};
class OutFile:public File{...};
class IOFile:public InFile,public OutFile{...};

任何时候你的继承体系中某个base class到某个derived class存在一条以上路径(例如上述File->IOFile就有两条路),那么你就要是不是要让base class 内的成员变量经过每一条路径被复制。例如假设File存在一个内部变量filename,从继承角度来看,IOFile应该有两份filename(一份继承自InFile,一份继承自OutFile)(观点1)。但是事实告诉我们不应该有两份 filename(观点2)。

奇怪的是,C++对于这两种观点,它都支持,其默认做法是属于第一种观点。如果你想要实现观点,必须要到虚继承:

class File{...};
class InFile:virtual public File{...};
class OutFile:virtual public File{...};
class IOFile:public InFile,public OutFile{...};

所以照正确的观点来说 ,public继承总是virtual public继承。也就是说当你需要public继承,都应改成用virtual public继承。事实是这样吗?显然不是的!因为通过virtual继承而来的对象会更大,访问会更慢。总之你的编译器会为virtual付出相应代价。还有更复杂的是,virtual base的初始化责任由继承体系的最底层 derived class负责。(相当于自底向上策略,而常规更简单的是自顶向下策略)。

当然多重继承体系在很多情况下是有用的。但是对于多重继承的建议是:多重继承只是一个工具而已,它相比单继承更加复杂,更加难以理解,所以能用多继承则尽量不用多重继承。

请记住

  1. 多重继承比单一继承复杂。他可能导致心得歧义,以及对virtual继承的需要。
  2. virtual继承会增加大小,速度,初始化(及赋值)复杂度等等成本。如果virtual base class不带任何数据,将是最有价值的情况。
  3. 多重继承确实有正当用途。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值