复合,继承,委托

来源:互联网 发布:电脑测温度软件 编辑:程序博客网 时间:2024/06/05 23:04

复合(Composition)

复合其实是一种 has-a 的关系,就是说一个类里面有其他类的对象
例如在STL标准库的实现中,queue里面有一个deque

template <class T>class queue {    //...protected:    deque<T> c;public:    //以下功能完全利用 c 的操作函数完成    bool empty() const { return c.empty(); }    size type size() const { return c.size(); }    //    void push(const value_type& x) { c.push_back(x); }    void pop() { c.pop_front(); }  };

queue的一些功能完全借助deque来实现。

复合关系下的构造与析构

  1. 构造函数是由内而外
    Container的构造函数首先调用Component的default构造函数(编译器帮助我们做的)
    然后才执行自己
          Container::Container{...}:Component(){...}
  1. 析构是由外而内
    Container的析构函数首先执行自己,然后才调用Component的析构函数
          Container::~Container{...}{... ~Component() };

如果不想调用另一个对象的默认构造函数,那就要显示调用

继承(Inheritance)

继承是一种 is-a 的关系,
基类中函数有三种:
- 普通函数
- 虚函数
- 纯虚函数
其中,如果在基类中写成纯虚函数,那么派生类(derived class)中一定要重新定义该函数,就是说派生类要有该虚函数的自己的版本
如果是虚函数,那么在基类中已经有了默认定义,派生类中可以选择重新定义。
public继承下,父类中的数据是被完全继承下来的。

继承关系的构造与析构

  1. 构造由内而外
  2. 析构由外而内

继承关系下构造与析构顺序与复合关系下相同。
当一个类同时有继承和复合时,是先调用基类的构造函数还是另一个复合的类的构造函数呢?
析构函数的顺序呢?谁先谁后并不重要,只是看一下。
一个测试程序看一下结果

#include <iostream>using namespace std;class Base{public:    Base()    {        cout << "I'm base class!" << endl;    }    ~Base()    {        cout << "Base dead!" << endl;    }};class Com{public:    Com()    {        cout << "I'm Composition class!" << endl;    }    ~Com()    {        cout << "Composition dead!" << endl;    }};class Test:public Base{public:    Test()    {         cout << "I'm Test class!" << endl;    }    ~Test()    {        cout << "Test class dead!" << endl;    }    Com ch;};int main(){    Test tt;    return 0;}

以下是在windows下使用Dev-c++,GCC 4.9.2的执行结果:
这里写图片描述
构造函数执行顺序是先执行基类的构造函数,再执行复合的对象的构造函数
析构函数执行顺序是先执行复合的对象的析构函数,再执行基类的析构函数
以上说明基类是“最里面的”
也刚好验证了上面所说的构造是由内到外,析构是由外到内

委托(Delegation)

A类中有一根指向另一个类B的指针
当创建A类对象时,B类对象并不被也创建,而在复合关系中,两个类的对象是同时创建
委托关系可以委托B类帮自己具体实现,

这种方法有个名词pImpl(Pointer to IMPLementation),简单理解就是接口与实现分离

(后面继续再整理)