一、构造函数的执行规则

C++构造函数的调用顺序为:

  1. 如果类中包含静态成员变量,先执行静态成员变量的构造函数。
  2. 如果类是派生类,则先执行基类的构造函数。同样如果基类也是一个派生类,也要先执行基类的构造函数。
  3. 执行成员变量中的构造函数,根据定义的顺序来,先执行类内初始化,再执行列表初始化。
  4. 执行本类的构造函数。

二、测试

定义一个英雄类hero,他们有一个名字作为成员变量,默认的名字就叫hero

class hero {
public:
    hero() : name("hero"){
        cout << "I'm " << name << endl;
    }

    hero(const string& name) : name(name){
        cout << "I'm " << name << endl;
    }

private:
    string name;
};

再定义一个战士类soldier继承于hero,他包含了2个英雄:Zed/Yasuo

class soldier : public hero {
public:
    soldier() : YaSUo("YaSuo"), Zed("Zed") {
        cout << "I'm soldier" << endl;
    }

private:
    hero Zed;
    hero YaSUo;
};

然后在主函数中定义一个战士对象:

int main() {
    soldier s;
    return 0;
};

执行程序,观察输出:

可以看到,最先输出的是hero,即父类的构造函数。然后输出Zed和YaSuo,虽然YaSuo在构造函数的初始化列表顺序中靠前,但是它的定义顺序低于Zed,所以还是先执行了Zed的构造函数然后再执行它。最后再执行soldier类本身的构造函数。

三、静态成员变量

当类中含有静态成员的时候,首先会执行静态成员变量的构造函数。

准确来说不能说是先执行静态成员的构造函数,而是在程序一开始就会执行静态成员的构造函数,因为静态变量都是一开始就分配好内存了,这个操作在b创建之前。

在soldier中添加一个静态成员LeeSin

class soldier : public hero {
    // ...
private:
    // ...
    static hero LeeSin;
};

hero soldier::LeeSin{"LeeSin"};

再次执行的结果:

能看到,LeeSin是最先构造的,它构造完成之后再执行了后面成员的构造函数。

最后修改:2020 年 01 月 10 日
如果觉得我的文章对你有用,请随意赞赏