• Effective C++改善程序与设计的55个具体做法 6. 继承与面向对象设计


    条款 32: 确定你的 public 继承塑模出 is-a 关系

    "public 继承"意味 is-a。适用于 base classes 身上的每一件事情一定也适用于derived classes 身上,因为每一个 derived class 对象也都是一个 base class 对象。

    个人理解:基类的函数适用于派生类的每一个函数。

    条款 33: 避免遮掩继承而来的名称

    derived classes 内的名称会遮掩 base classes 内的名称。在 public 继承下从来没有人希望如此。

    为了让被遮掩的名称再见天日,可使用 using 声明式或转交函数( forwarding functions)。

    个人理解:相同名称会有覆盖的问题,public 继承可以用using 声明, private函数可以使用转交函数。

    条款 34: 区分接口继承和实现继承

    接口继承和实现继承不同。在 public 继承之下, derived classes 总是继承 base class的接口。

    pure virtual 函数只具体指定接口继承。

    简朴的(非纯) impure virtual 函数具体指定接口继承及缺省实现继承。

    non-virtual 函数具体指定接口继承以及强制性实现继承。

    个人理解:接口继承只继承函数接口,实现继承继承接口和实现、并且又能够重写;

    条款 35: 考虑 virtual 函数以外的其他选择

    virtual 函数的替代方案包括 NVl 手法及 Strategy 设计模式的多种形式。 NVI 于法自身是一个特殊形式的 Template Method 设计模式.

    将机能从成员函数移到 class 外部函数,带来的一个缺点是,非成员函数无法访问 class 的 non-public 成员。

    std::function 对象的行为就像→般函数指针。这样的对象可接纳"与给定之目标签名式 (target signature) 兼容"的所有可调用物 (callable entities)。

    个人理解:

    1. 使用NVI手法,他是用public non-virtual成员函数包裹较低访问性(privateprotected
    2. virtual函数;
    3. virtual函数替换成“函数指针成员变量”,这是strategy设计模式的一种表现形式;
    4. ****以tr1::function成员变量替换virtual函数,因而允许使用任何可调用物(callable entity)
    5. 搭配一个兼容与需求的签名式,这也是strategy设计模式的某种形式;
    6. 将继承体系内的virtual函数替换成另一个继承体系内的virtual函数。这是strategy设计模式的传统做法;

    条款 36: 绝不重新定义继承而来的 non-virtual 函数

    绝对不要重新定义继承而来的 non-virtual 函数

    个人理解:继承类会覆盖基类中函数实现;

    条款 37: 绝不重新定义继承而来的缺省参数值

    绝对不要重新定义一个继承而来的缺省参数值,因为缺省参数值都是静态绑定,而virtual函数一一你唯一应该覆写的东西一一却是动态绑定。

    个人理解:

    1. class Shape{
    2. public:
    3. enum ShapeColor {Red, Green, Blue};
    4. virtual void draw(ShapeColor color=Red) const = 0;
    5. };
    6. class Rectangle : public Shape{
    7. public:
    8. virtual void draw(ShapeColor color=Green) const;//和父类的默认参数不同
    9. }
    10. Shape* pr = new Rectangle; // 注意此时pr的静态类型是Shape,但是他的动态类型是Rectangle
    11. pr->draw(); //virtual函数是动态绑定,而缺省参数值是静态绑定,**所以会调用Red,而不是green**
    12. class Rectangle : public Shape{
    13. public:
    14. virtual void draw(ShapeColor color= Red) const; //**(代码重复且带有相依性,不可取)**
    15. }
    16. **//可以更换为NVI的手法可以实现目的**
    17. class Shape{
    18. public:
    19. enum ShapeColor {Red, Green, Blue};
    20. void draw(ShapeColor color=Red) const {
    21. doDraw();
    22. }
    23. private:
    24. virtual void doDraw(ShapeColor color) const = 0;
    25. };
    26. class Rectangle : public Shape{
    27. public:
    28. virtual void doDraw(ShapeColor color) const;
    29. }

    条款 38: 通过复合塑模出 has-a 或"根据某物实现出”

    复合( composition) 的意义和 public 继承完全不同。

    在应用域 (application domain) ,复含意味 has -a (有一个)。在实现域(implementation domain) ,复合意味 is-implemented-in-terms-of(根据某物实现出)。

    个人理解:

    1. //应用领域:
    2. class Address {...};
    3. class PhoneNumber {...};
    4. class Person {
    5. ...
    6. private:
    7. std::string name;
    8. Address address;
    9. PhoneNumber phone;
    10. }
    11. //实现域:set并不是一个list,但是set可以has a list:
    12. template<class T>
    13. class Set{
    14. public:
    15. void insert();
    16. //.......
    17. private:
    18. std::list rep;
    19. }

    条款 39: 明智而审慎地使用 private 继承

    Private 继承意味 is-implemented-in-terms of (根据某物实现出)。它通常比复合(composition) 的级别低。但是当 derived class 需要访问 protected base class 的成员,或需要重新定义继承而来的virtual 函数时,这么设计是合理的。

    和复合( composition) 不同, private 继承可以造成 empty base 最优化。这对致力于"对象尺寸最小化"的程序库开发者而言,可能很重要。

    个人理解:如果D以private形式继承B,private继承意味着只有实现部分被继承,而没有其他含义。尽可能的使用复合,必要时才使用private(总结中提到的两种情况)

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

    多重继承比单一继承复杂。它可能导致新的歧义性,以及对 virtual 继承的需要。

    virtual 继承会增加大小、速度、初始化(及赋值)复杂度等等成本。如果 virtual base classes 不带任何数据,将是最具实用价值的情况。

    多重继承的确有正当用途。其中一个情节涉及"public 继承某个 Interface class" 和 "private 继承某个协助实现的class" 的两相组合。

    个人理解:多重继承基类对象存在多个

  • 相关阅读:
    大数据测试入门介绍
    【Python项目】毕业设计必备——Python实现一个GUI版本的学生信息管理系统 | 附源码
    涂鸦TuyaOS SDK 网关历程-wifi配网
    「Verilog学习笔记」实现3-8译码器①
    1001 害死人不偿命的(3n+1)猜想Java
    Layui快速入门之第九节 表格事件的使用
    舞伴问题,棋盘覆盖问题
    【小程序】常见系统API | 页面分享 | 位置信息 | 本地存储
    BeeWare官方教程中文版
    30天Python入门(第十七天:深入了解Python中的异常处理)
  • 原文地址:https://blog.csdn.net/weixin_35762621/article/details/125881348