# [19] 继承 — 基础
## FAQs in section [19]:
* [19.1] 对于C++,继承是否重要?
* [19.2] 何时该使用继承?
* [19.3] 在C++中如何表达继承?
* [19.4] 将一个派生类型的指针转换成它的基类型可以吗?
* [19.5] `public:`, `private:`和 `protected:`有什么不同?
* [19.6] 为什么派生类不能访问基类的`private:`成员?
* [19.7] 如何才能在改变类的内在部分时,保护其派生类不被破坏?
## 19.1 对于C++,继承是否重要?
是。
继承是面向对象编程和抽象数据类型(ADT)编程的区分标志
## 19.2 何时该使用继承?
作为一种特化的机制。
人们抽象事物有两种角度:“部分”和“种类”。Ford Taurus是一种(is-a-kind-of-a)汽车,并且 Ford Taurus 有(has-a)引擎,轮胎等。“部分”层次已经随着ADT风格而成为软件系统的一部分。继承则增加了另一种分解的角度。
## 19.3 在C++中如何表达继承?
通过 `:public` 语法:
```
class Car : public Vehicle {
public:
// ...
};
```
我们有几种方式声明以上的关系:
* `Car` 是 “一种”("a kind of a")`Vehicle(交通工具)`
* `Car` 起源于("derived from")`Vehicle`
* `Car` 是一种特殊化的("a specialized") `Vehicle`
* `Car` 是`Vehicle`的一个子类("subclass")
* `Car` 是`Vehicle`的一个派生类(“derived class”)
* `Vehicle` 是`Car`的基类("base class")
* `Vehicle` 是`Car` 的超类("superclass")(这在C++ 社群中不常用)
(注意: 本 FAQ 的论述仅与公有继承(`public` inheritance)有关; 私有和保护继承并不相同)
## 19.4 将一个派生类型的指针转换成它的基类型可以吗?
可以。
派生类对象是基类对象的一种。因此从派生类指针到基类指针的转换是非常安全的,并且始终会发生。例如,如果有一个 car 类型的指针,而实际上指向了 vehicle,这种从 `Car*` 到 `Vehicle*` 的转换是非常安全的和常规的:
```
void f(Vehicle* v);
void g(Car* c) { f(c); } // 非常安全; 不用转换
```
(注意: 本 FAQ 的论述仅与公有继承(`public` inheritance)有关; 私有和保护继承并不相同)
## 19.5 `public:`, `private:`和 `protected:`有什么不同?
* 在类的`private:`节中声明的成员(无论数据成员或是成员函数)仅仅能被类的成员函数和友元访问。
* 在类的`protected:` 节中声明的成员(无论数据成员或是成员函数)仅仅能被类的成员函数,友元以及子类的成员函数和友元访问。
* 在类的`public:`节中声明的成员(无论数据成员或是成员函数)能被任何人访问。
## 19.6 为什么派生类不能访问基类的`private:`成员?
为了使派生类在将来基类改变时不受影响。
派生类无法访问基类的私有成员。这样在对基类私有成员作任何改变时,就有效地锁定了派生类。
## 19.7 如何才能在改变类的内在部分时,保护其派生类不被破坏?
类有两套截然不同的接口,它们分别面向两个截然不同的客户:
* 有为无关类服务的`public:` 接口
* 有为派生类服务的`protected:` 接口
除非你期望你的所有子类全部由你自己的团队建立,否则你应该考虑让基类部分成为`private:`,并且用 `protected:`来内联供子类访问基类私有数据的访问函数。使用这种方法,私有部分可以被改变,但是派生类的代码不会被破坏(除非你改变了`protected`的访问函数)。
- C++ FAQ Lite
- [1] 复制许可
- [2] 在线站点分发本文档
- [3] C++-FAQ-Book 与 C++-FAQ-Lite
- [6] 综述
- [7] 类和对象
- [8] 引用
- [9] 内联函数
- [10] 构造函数
- [11] 析构函数
- [12] 赋值算符
- [13] 运算符重载
- [14] 友元
- [15] 通过 <iostream> 和 <cstdio>输入/输出
- [16] 自由存储(Freestore)管理
- [17] 异常和错误处理
- [18] const正确性
- [19] 继承 — 基础
- [20] 继承 — 虚函数
- [21] 继承 — 适当的继承和可置换性
- [22] 继承 — 抽象基类(ABCs)
- [23] 继承 — 你所不知道的
- [24] 继承 — 私有继承和保护继承
- [27] 编码规范
- [28] 学习OO/C++
- [31] 引用与值的语义
- [32] 如何混合C和C++编程
- [33] 成员函数指针
- [35] 模板
- [36] 序列化与反序列化
- [37] 类库