Copy Constructor的构造操作
Copy Constructor的构造操作
有三种情况,会以一个object的内容作为另一个class object的初值:
1、 对一个object做显式的初始化操作
class X{…};
X a;
X b = a;
2、当object被当做参数交给某个函数:
X a;
void foo(X x);
foo(a);
3、 当返回值为object:
X foo
{
X a;
return a;
}
假设class X显式定义了一个copy constructor,类似下面这样:
X::X(const X& x);
则在大部分情况下,当一个class object以另一个同类实例作为初值,上述的copy constructor就会被调用。
那如果class没有提供一个explicit copy constructor的话,编译器是如何处理的呢?这时就要所谓的default memberwise initialization起作用了。default memberwise initialization也就是把object内每一个内建的或派生的data member的值,拷贝到另一个object,对于member class object,则以递归的方式继续实施memberwise initialization。从对象的数据成员角度出发,具体到对象的每一个数据成员的操作,编译器通常采用(可以认为就是)bitwise copy(按位拷贝)操作,就像memcpy或者memset函数一样,原样将内存中的数据按位复制一份。但是并不是所有不提供explicit copy constructor的class都会展现bitwise copy。
像default constructor,C++ Standard把copy constructor区分为trivial和nontrivial两种。其中nontrivial copy constructor才会被编译器真正合成与程序之中,而trivial copy constructor实际上被没有被真正合成。决定copy constructor是否为trivial的标准对应的class是否展现出bitwise copy。
那什么情况下,copy constructor是nontrivial,或者说class不展现bitwise copy呢?分为以下4中情况:
第一、当class内含有一个member object,而后者的class有一个copy constructor(无论是显式声明,还是编译器隐式合成)。
因为编译器必须将member object的“copy constructor的调用操作”安插到被编译器合成的copy constructor中,否则无法调用member object的copy constructor。
第二、当class继承自一个base class,而后者存在一个copy constructor(无论是显式声明,还是编译器隐式合成)。
因为编译器必须将base class的“copy constructor的调用操作”安插到被编译器合成的copy constructor中,否则无法调用base class的copy constructor。
第三、当class声明了至少一个virtual function。
当class至少有一个virtual function时,这个class的object必然会有virtual table和virtual point。所以对于每一个新产生的class object的virtual point,必须正确设定初值。如果采用bitwise copy,在一般情况下是可以满足要求的。但是当一个base class object以其derived class的object内容做初始化时,如果采用bitwise copy的话,virtual point就难以保证安全,因为从derived class object拷贝过来的virtual point指向的还是derived class的virtual table,而并不是base class的virtual table。
第四、当class直接或间接地继承了至少一个virtual base class。
每一个编译器对于虚拟继承的支持承诺,都代表必须让derived class object中的virtual base class subobject位置在执行期就准备妥当。但bitwise copy 可能会破坏这个位置,所以编译器在这种情况不会采用bitwise copy。
总结,以上4种情况下class不再保持bitwise copy,而且explicit copy constructor未被声明,编译器为了正确处理“以一个class object作为另一个class object的初值”,会为class合成nontrivial copy constructor。
Copy Constructor的构造操作的更多相关文章
- 构造函数语义学——Copy Constructor 的构造操作
前言 在三种情况下,会以一个 object 的内容作为另一个 class object 的初值: object明确初始化 class X{...}; X x; X xx = x; object 被当作 ...
- 深度探索C++对象模型之第二章:构造函数语意学之Copy constructor的构造操作
C++ Standard将copy constructor分为trivial 和nontrivial两种:只有nontrivial的实例才会被合成于程序之中.决定一个copy constructor是 ...
- Default Constructor的构造操作
Default Constructor的构造操作 C++ Annotated Reference Manual书中的Section 12.1说过:default constructor 只有在编译器需 ...
- 深度探索C++对象模型之第二章:构造函数语意学之Default constructor的构造操作
C++新手一般由两个常见的误解: 如果任何class没有定义默认构造函数(default constructor),编译器就会合成一个来. 编译器合成的的default constructor会显示的 ...
- 构造函数语义学之Copy Constructor构建操作(2)
二.详述条件 3 和 4 那么好,我又要问大家了,条件1 和 2比较容易理解.因为member object或 base class 含有copy constructor.那么member objec ...
- 构造函数语义学之Copy Constructor构建操作(1)
一.Copy Constructor的构建操作 就像 default constructor 一样,如果class没有申明一个 copy constructor,就会隐含的声明或隐含的定义一个.生成的 ...
- C++-copy constructor、copy-assignment operator、destructor
本文由@呆代待殆原创,转载请注明出处. 对于一个类来说,我们把copy constructor.copy-assignment operator.move constructor.move-assig ...
- C++对象模型——Default Constructor的建构操作(第二章)
第2章 构造函数语意学 (The Semantics of Constructor) 关于C++,最常听到的一个抱怨就是,编译器背着程序猿做了太多事情.Conversion运算符就是最常被引用的 ...
- copy constructor
copy constructor也分为trivial和nontrivial两种 如果class展现出bitwise copy semantics(按位拷贝语义),则不会构造出 copy constru ...
随机推荐
- uinavigationcontroller uinavigationbar 下方横线去除
#import "QKBaseNavigationController.h" #define fontSize 19 @interface QKBaseNavigationCont ...
- jquery 复选框
jquery 选中复选框 $("input[type='checkbox']").prop("checked", true); jquery 判断复选框是否被选 ...
- 大型网站技术架构 核心原理与案例分析 pdf
需要的小伙伴拿去,哈哈.百度云链接:https://pan.baidu.com/s/1hsuiM3q
- vs2008编译FileZilla客户端源码
vs2008编译FileZilla客户端源码 下载FileZilla客户端源码,下载地址https://download.filezilla-project.org/. FileZilla客户端解决方 ...
- jQuery(4)—— jQuery中的事件
jQuery中的事件 [加载DOM] 在常规的JavaScript代码中,通常使用window.onload方法,在jQuery中,使用的是$(document).ready()方法.极大地提高了we ...
- Golang的"泛型"模式
只要实现了Sortable接口的所有方法,就可以使用该接口的函数. 我们通过冒泡排序来演示一下: package main import "fmt" type Sortable i ...
- PHP学习过程_Symfony_(2)
今天正式学习Symfony;首先推荐一篇文章"十分钟学习Symfony"(这是我们老大写的,由于那些搞seo的家伙的粘贴复制也不写出处,老大干脆把代码库给清理了,不过幸好我提前fo ...
- Google科学家前腾讯副总裁吴军将出席第二届万物互联创新大会
当越来越多的科技产品注入互联网的基因,"万物互联"的模式悄然兴起.第二届万物互联创新大会(B12大会)将于2016-11-13日在杭州市余杭区隆重召开.Google科学家前腾讯副总 ...
- 2016年团体程序设计天梯赛-决赛 L1-5. 是不是太胖了(5)
据说一个人的标准体重应该是其身高(单位:厘米)减去100.再乘以0.9所得到的公斤数.已知市斤是公斤的两倍.现给定某人身高,请你计算其标准体重应该是多少?(顺便也悄悄给自己算一下吧……) 输入格式: ...
- EMPTY isset unset var_dump 用法
empty 判断一个变量是否为空,返回布尔值 isset isset 判断一个值是否存在 unset取消变量设置, var_dump 打印变量并类型