zoukankan      html  css  js  c++  java
  • 构造函数语意学

    1. default constructors 在需要的时候被编译器产生出来。 Global objects的内存保证会在程序激活的时候被清为0.Local objects配置于程序的堆栈中,heap objects配置于自由空间中,都不一定会被清为0,它们的

    内容是内存上次被使用后的遗迹。

    2. 编译器生成nontrivial constructor

    (1) 带有Default Constructor的Member Class Object

    如果一个class没有任何constructor,但它内含一个member object,而后者有default constructor,那么这个class的implicit default constructor就是nontrivial,编译器需要为此class合成一个default constructor.

    如果有多个class member objects要求constructor初始化操作,编译器将为每一个constructor安插程序代码,以member声明次序调用每一个member所关联的default constructors。

    (2) 带有Default Constructor的Base Class

    如果一个没有任何constructors的class派生自一个带有default constructor的base class,那么这个derived class的default constructor会被视为nontrivial,因此需要被合成出来。它将调用上一层base classes的

    default constructor。

    (3) 带有一个virtual function的class

    class声明或继承一个virtual function;

     1 class Widget {
     2 public:
     3     virtual void flip() = 0;
     4 };
     5 
     6 void flip(const Widget& widget) {
     7     widget.flip();
     8 }
     9 
    10 void foo() {
    11     Bell b;
    12     Whistle w;
    13 
    14     flip(b);
    15     flip(w);
    16 }

    下面两个操作会在编译器间发生:

    一个virtual function table会被编译器产生出来,内放class的virtual functions地址。

    在每一个class object中,一个额外的pointer member会被编译器合成出来,内含相关的class vtbl的地址。

    class派生自一个继承串链,其中有一个或更多的virtual base classes.

    必须使virtual base class在其每一个derived class object中的位置,能够于执行期准备妥当。对于class所定义的每一个constructor,编译器安插那些“允许每一个virtual base class的执行期存取操作”的码,如果class没有声明任何constructors,编译器必须为它合成一个default constructor。

    Copy Constructor 的建构操作

    有三种情况,会以一个object的内容作为另一个class object的初值。最明显的一种情况是对一个object做明确的初始化操作:

    class X {};

    X x;

    另两种情况是当object被当作参数交给某个函数时,如:

    1 extern void foo(X x);
    2 
    3 void bar() {
    4     X xx;
    5     foo(xx);  // 以x作为foo()第一个参数的初值
    6 }

    以及当函数传回一个class object时,如:

    X foo_bar() {
        X xx;
        return xx;
    }

    Bitwise Copy Semantics(位逐次拷贝)

    只有nontrivial的实体才会被合成于程序之中,决定一个copy constructor是否为trivial的标准在于class是否展现出所谓的bitwise copy semantics。

    什么时候一个class不展现出 bitwise copy semantics:

    (1)当class内含一个member object而后者的class声明有一个copy constructor时;

    (2)当class继承自一个base class而后者存在有一个copy constructor时;

    (3)当class声明了一个或多个virtual functions时;

    (4)当class派生自一个继承串链,其中有一个或多个virtual base classes时。

    前两种情况中,编译器必须将member或base class的copy constructors调用操作安插到被合成的copy constructor中。

    对于3,合成出来的copy constructor会明确设定object的vptr指向其类的virtual table,而不是直接从右手边的class object中将其vptr现值拷贝过来。

    对于4,一个class object如果以另一个object为初值,而后者有一个virtual base class subobject,那么也会使bitwise copy semantics失效。

    每个编译器对于虚拟继承的支持承诺,都表示必须让derived class object中的virtual base class subobject位置在执行期就准备妥当。

    成员初始化列表

    一下情况必须使用成员初始化列表:

    (1)当初始化一个reference member时;

    (2)当初始化一个const member时;

    (3)当调用一个base class的constructor,而它拥有一组参数时;

    (4)当调用一个member class的constructor,而它拥有一组参数时。

    编译器会操作initialization list,以适当次序在constructor之内安插初始化操作,并且在任何explicit user code之前。list中的项目次序是由class中的members声明次序决定,不是由initialization list中的排列次序决定。

  • 相关阅读:
    TCL环境检查
    POI之Excel文档增删改查
    wireshark自动化之tshark命令行
    selenium-webdriver
    ruby自动化之selenium webGUI
    TCL自动化之SSH交互式
    链表的操作
    参考网址
    RTC定时开机闹钟
    中断
  • 原文地址:https://www.cnblogs.com/sssblog/p/13711231.html
Copyright © 2011-2022 走看看