二、构造/析构/赋值运算

05.了解C++默默编写并调用那些函数

如果自己不声明, 编译器就会暗自为class创建一个default构造函数、一个copy构造函数、一个copy assignment操作符(代码合法有意义时编译器才会生成),以及一个析构函数

并且所有的这些都是public且inline的。

若你自定义了构造函数,编译器就不会为你创建default构造函数。

注:base class如果把copy构造函数或copy assignment操作符设置为private,derived class将拒绝生成copy构造函数或copy assignment操作符。

06.若不想使用编译器自动生成的函数,明确拒绝它

  1. 可以将copy构造函数或copy assignment 函数声明为private并且不予实现,可阻止编译器暗自创建其专属版本,也可阻止人们调用它。
  2. 继承专门为了阻止coping动作而设计的base class。

07.为多态基类声明virtual析构函数

polymorphic(带多态性质的)base classes才应该声明一个virtual析构函数(免除“局部销毁”问题),不为多态用途的base classes不该声明virtual 析构函数。

原因:当派生类对象经由一个基类指针而被删除,而该基类带着一个non-virtual析构函数时,实际执行无法销毁对象的派生类成分。但实现虚函数对象需要额外携带某些信息,是由一个vptr指针,vptr指向一个有函数指针构成的数组vtbl(虚函数表),实际被调用的函数却决于该对象的vptr所指的vtbl——编译器在其中寻找适当的函数指针。

需要额外空间。

08.别让异常逃离析构函数析构函数绝对不能抛出异常

1. 析构函数绝对不能抛出异常;如果一个被析构函数调用的函数可能抛出异常,析构函数应该捕捉任何异常,然后吞下它们(不传播)或结束程序

2. 如果客户需要对某个操作函数运行期间抛出的异常做出反应,那么类应该提供一个普通函数(而非在析构函数中)执行该操作

注:

如果析构函数抛出异常,可能导致两个异常同时存在,程序若不是结束执行就是导致不明确行为。

09.绝不在构造和析构过程中调用virtual函数

由于无法使用virtual函数从base classes向下调用,可以令derived classes将必要的构造信息向上传递至base class构造函数替换

注:

base class构造期间virtual函数绝不会下降到derived classes阶层,原因有二:

1. base class构造或析构函数执行时derived class的成员变量尚未初始化,如果调用的virtual函数下降到derived class阶层,必定导致使用的成员变量未初始化

2. 在derived class的base class构造期间,对象的类型是base class,不会成为一个derived class对象

10.令operator=返回一个refference to *this

赋值可以写成连锁形式:x = y = z = 15;

而为了实现这样的连锁赋值,赋值操作符必须返回一个reference指向操作符的左侧实参。

11.在operator= 中处理“自我赋值”

加一个“证同测试”使具有“自我赋值安全性”。

为了防止自我赋值,可能有两个不同的对象指向一个地址,为了防止在释放一个对象资源时,使得另一个变为野指针,需要对自我赋值处理。

精心安排的语句可以使代码具有“异常安全性”(自动获得“自我赋值安全性”):在复制构造之前别删除原指针

另一种替代方案是“copy and swap”技术

12.复制对象时勿忘每一个成分

1. copying函数应确保复制对象内的所有成员变量以及所有base class成分。

2.不要尝试以一个copying函数实现另一个copying函数。应将共同机能放进第三个函数中并由它们共同调用。

编写拷贝构造函数时,如果子类继承父类,子类的拷贝构造、赋值都需要对父类中成分再复制或者初始化。

Effective C++ 总结笔记(二)的更多相关文章

  1. 《CMake实践》笔记二:INSTALL/CMAKE_INSTALL_PREFIX

    <CMake实践>笔记一:PROJECT/MESSAGE/ADD_EXECUTABLE <CMake实践>笔记二:INSTALL/CMAKE_INSTALL_PREFIX &l ...

  2. jQuery源码笔记(二):定义了一些变量和函数 jQuery = function(){}

    笔记(二)也分为三部分: 一. 介绍: 注释说明:v2.0.3版本.Sizzle选择器.MIT软件许可注释中的#的信息索引.查询地址(英文版)匿名函数自执行:window参数及undefined参数意 ...

  3. Mastering Web Application Development with AngularJS 读书笔记(二)

    第一章笔记 (二) 一.scopes的层级和事件系统(the eventing system) 在层级中管理的scopes可以被用做事件总线.AngularJS 允许我们去传播已经命名的事件用一种有效 ...

  4. Python 学习笔记二

    笔记二 :print 以及基本文件操作 笔记一已取消置顶链接地址 http://www.cnblogs.com/dzzy/p/5140899.html 暑假只是快速过了一遍python ,现在起开始仔 ...

  5. WPF的Binding学习笔记(二)

    原文: http://www.cnblogs.com/pasoraku/archive/2012/10/25/2738428.htmlWPF的Binding学习笔记(二) 上次学了点点Binding的 ...

  6. webpy使用笔记(二) session/sessionid的使用

    webpy使用笔记(二) session的使用 webpy使用系列之session的使用,虽然工作中使用的是django,但是自己并不喜欢那种大而全的东西~什么都给你准备好了,自己好像一个机器人一样赶 ...

  7. AJax 学习笔记二(onreadystatechange的作用)

    AJax 学习笔记二(onreadystatechange的作用) 当发送一个请求后,客户端无法确定什么时候会完成这个请求,所以需要用事件机制来捕获请求的状态XMLHttpRequest对象提供了on ...

  8. 《MFC游戏开发》笔记二 建立工程、调整窗口

    本系列文章由七十一雾央编写,转载请注明出处.  http://blog.csdn.net/u011371356/article/details/9300383 作者:七十一雾央 新浪微博:http:/ ...

  9. JavaScript基础笔记二

    一.函数返回值1.什么是函数返回值    函数的执行结果2. 可以没有return // 没有return或者return后面为空则会返回undefined3.一个函数应该只返回一种类型的值 二.可变 ...

  10. [Firefly引擎][学习笔记二][已完结]卡牌游戏开发模型的设计

    源地址:http://bbs.9miao.com/thread-44603-1-1.html 在此补充一下Socket的验证机制:socket登陆验证.会采用session会话超时的机制做心跳接口验证 ...

随机推荐

  1. JS获取contextPath的方法

    function getContextPath() { var pathName = document.location.pathname;    var index = pathName.subst ...

  2. 深入浅出WPF-08.Event( 事件)01

    事件(Event) 首先我们来继续说一下UI组件树,因为WPF事件 的路由环境就是组件树.WPF中的树有两种,一种是逻辑树(Logical Tree),一种是可视元素树(Visual Tree).逻辑 ...

  3. 记一次centos挂载ceph存储的坑

    起因 生产有两台服务器,准备用来跑工作流,执行的资源的是放在ceph存储集群中,第一步挂载ceph 执行命令:mount -t ceph xxx:xxx -o name=admin,secret=AQ ...

  4. 【C++ Primer Plus】编程练习答案——第4章

    1 void ch4_1() { 2 using namespace std; 3 string fname, lname; 4 char grade; 5 unsigned int age; 6 c ...

  5. IDEA远程部署调试Java应用程序

    IDEA远程部署调试Java应用程序 目录 IDEA远程部署调试Java应用程序 基本概述 准备工作 远程服务器准备 安装JDK 配置JAVA_HOME 项目准备 创建一个SpringBoot项目 创 ...

  6. vue组件的生命周期详解

    1.生命周期&生命周期函数 生命周期:指一个组件从创建->运行->销毁的整个阶段,强调的是一个时间段. 生命周期函数:由vue框架提供的内置函数,会伴随着组件的生命周期,自动按序执 ...

  7. uniapp内嵌H5页面和uniapp页面相互传值

    最近项目有一个需求 -- 做一个百人抽奖的模块,要求展示百人的头像并且不断变化排列组合 先展示一部分的用户头像,然后每增加一个用户就增加一个头像在百人排列里面 我整一个gif图来展示一下 大概就是这种 ...

  8. Codeforces Round #747 (Div. 2)

    比赛地址 A(水题) 题目链接 题目: 给出指定\(n\),求解出一段区间\([l,r]\)使得\(\sum\limits_{i=l}^ri=n\) 解析: 从点0,1两点作为起点分别向左右延伸长度, ...

  9. TypeScript 枚举指南

    枚举是受 TypeScript 支持的数据类型.枚举允许您定义一组命名常量.使用它们可以更轻松地记录意图或创建一组不同的案例.枚举大多数用于面向对象的编程语言(如 Java 和 C#)中,现在也可以 ...

  10. HttpServletResponse 入门

    继承体系 功能: 设置响应消息 1. 设置响应行 格式:HTTP/1.1 200 ok 设置状态码:setStatus(int sc) 2. 设置响应头:setHeader(String name, ...