深度探索C++对象模型读书笔记(二)构造函数语义学

首先是一些阅读本章所需要的英文术语:

这一章主要讲述构造函数以及拷贝构造函数在C++中的实现细节,有助于我们认识C++编译器在涉及对象构造时的底层操作。

构造函数

Default Constructor的建构操作

默认构造函数在需要的时候被编译器产生出来。对于下图所示bar对象,并不会有默认构造函数进行调用,其数据成员依然是未定义状态。

 

用书上的话来讲就是右上图所示,由于该类不存在用户定义的构造函数,所以编译器会隐式生成一个构造函数,但这个构造函数并不存在任何实际代码,被认为是trivial(无用的)。

我对这句话的理解是:对象在构造过程中构造函数所起的是对构造过程的实际控制作用,如果编译器生成的构造函数并没有实际执行内容,则其就是无用的,和没生成一样。

          上例中,由于Foo类的两个成员都是内置类型,自动生成的构造函数并不会有任何动作,自然就是trivial的。

有4中情况下编译器生成的默认构造函数是nontrivial的,也就是有实际构造动作的:

1.带有Default Constructor 的Member Class Object(非静态数据成员带有默认构造函数的对象)

    这种对象的构造函数里面必须有相应的代码调用类数据成员的构造函数进行初始化。这些代码被安插在原先那个默认的trivial构造函数中,使之成为nontrivial,同时若对象中有多个member object则编译器会按照其在class中的声明顺序依次调用default constructor。

2.带有Default Constructor的Base Class(基类带有默认构造函数的对象)

  和上面的道理类似,基类的成员需要被显式构造,这就要求子类的默认构造函数有对于父类的显式调用,这些代码将被安插在自动生成的构造函数中。

3.带有一个Virtual Function的Class

  下面两种情况也需要合成一个default constructor(nontrivial)

  1) class 声明(或继承)一个virtual function。

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

这个主要是考虑到带虚函数的对象内保存有一个指向虚函数表的指针,这个指针在发生子类型赋值给子类型的时候会出现问题,编译器必须在进行这种操作的时候安排适当的代码完成相应虚函数指针的赋值。编译器需要保证每个带虚函数的类对象其虚函数指针指向正确的地址。

4.带有一个Virtual Base Class的Class

虚继承设计多重继承,这里并不想设计,有兴趣可以参考该书P46

 

拷贝构造函数

1.Default Memberwise Initialization

当class没有提供显式拷贝构造函数时,C++会默认复制每个内建的数据,对于其中的member class object则会递归施行memberwise initialization。

和构造函数类似,拷贝构造函数同样具有trivial和nontrivial两种,只有nontrivial的才会被实际合成出来进行调用。两者的区别则是该函数是否属于bitwise copy semantics语义。即所有拷贝都只是按位操作。

2.bitwise copy semantics(位逐次拷贝)

产生条件和上述产生nontrivial构造函数类似

不产生bitwise copy语义的情况如下:

当一个子类型赋值给父类型的时候如果按照bitwise方式进行复制,则父类型的vptr的指针将会出现错误,如下图所示。所以需要一个nontrivial的复制构造函数对其进行相关设置。

 

 

 程序转化语义学

主要分析了对象被作为参数传递或者作为返回值返回时C++编译器对于这些参数传递的实现以及优化。

参数传递时拷贝构造以及对象的传递:

 

         

返回值的初始化:

           

成员们的初始化队伍(Member Initialization List)

当出现以下情况时必须使用初始化列表:

初始化列表中成员初始化顺序是按照成员在类中的声明顺序进行的,而不是在初始化列表中的顺序!初始化列表中也已出现函数调用,但程序员需要确保其逻辑正确

 

转载于:https://www.cnblogs.com/J1ac/p/9088478.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值