6、继承与面向对象设计
条款32:确定你的public继承塑模出is-a关系
“public继承”意味is-a。适用于基类身上的每一件事一定也适用于派生类身上,因为每一个派生类对象也都是一个基类对象。
条款33:避免遮掩继承而来的名称
就如函数作用域内的变量会掩盖函数作用域外的同名变量一样。派生类中如果声明了与基类中同名的函数(无论是虚、非虚,还是其他形式),都会掩盖掉基类中的所有同名函数(只是函数名字相同),注意,是所有,包括参数不同的重载函数,都会不再可见。此时再通过子类使用其基类中的重载函数(子类没有声明接收该参数的重载函数时),都会报错。解决方法有两种:
一、是使用using声明式来在子类中声明父类的同名函数(重载函数不需要声明多个),此时父类的各重载函数就是子类可见的了。如:
class Derived: public Base{
public:
using Bade::mf; //让基类内名为mf的所有东西再派生类作用域内都可见(并且public)
void mf(int x); //派生类自己的mf
...
};
Derived d;
int x = 0;
d.mf(); //调用基类的mf函数
d.mf(x); //调用派生类自己的mf函数
二、是使用转交函数,即在子类函数的声明时进行定义,调用父类的某个具体的重载函数(此时由于在声明时定义,成为inline函数),此举可以只让需要的部分父类重载函数于子类可见。如:
class Base{
public:
virtual void mf1() = 0;
virtual void mf1(int);
...
};
class Derived: private Base{
public:
virtual void mf1(){