1:确保对象被使用前已先被初始化,读取未初始化的值会造成不明确的行为,可能导致程序终止运行或者其他不可预期的现象;在C++中,当你使用C part of C++(C++中C语言部分的内容)且初始化可能导致运行期成本,那么就不会保证一定初始化,而non-C part of C++,系统却能保证被初始化。对于内置类型(C++定义算术类型(整型和浮点型)和空类型为内置类型),需要手动完成初始化;对于自定义类型,需要用构造函数完成相应的初始化工作;

2:区分赋值(assignment)操作和初始化(initialization)的行为,在实现相同功能的情况下尽可能的使用初始化的方式

对象成员的初始化动作发生在进入构造函数之前,进入构造函数本体之前,成员变量自动调用自己的default构造函数完成默认初始化(不使用初始化列表的情况下),然后进入函数体执行对应的功能;

针对上述情况,使用成员初始化列表(member initialization list)替换常规的赋值操作可以省去一个赋值操作的过程,直接实现以各个成员变量的实参拷贝构造给形参,初始化列表中应包含所有的成员变量;

对于大多数类型而言,比起先调用default构造函数后调用copy assignment操作符,只调用一次copy构造函数是比较高效的,但对于内置类型,其初始化和赋值的成本相同,但为了一致性效果,都采用初值化列表的形式;

如果成员变量是const或者references,那么就一定需要初值,而不能被赋值

初始化列表的初始化顺序是按照成员变量的定义顺序进行初始化的,与初始化列表中变量如何排列无关;

    结论:初始化时,使用初始化列表可以使你的程序更加高效;当我们想要用default构造成员变量的时候,我们也可以指定成员初始列,只要指定初始化实参为空就行;

3:当classes中有多个构造函数时,每个构造函数有自己的成员初始列,那么这样就可能出现重复的初值列,这种情况下可以将初始值列中那些“赋值表现像初始化一样好”的成员变量,改用它们的赋值操作,并把这些赋值操作合并成一个函数(通常是private)来供所有的构造函数使用;

4:static对象,其寿命从被构造出来到程序结束为止。通常函数内的static对象称为local static对象,其他的static对象称为non-local static对象;

问题:当某个编译单元内的某个非non-local static对象的初始化动作使用了另一个单元内的的某个non-local static对象,可能所用到的这个对象可能没有初始化,而且C++对这个初始化的顺序没有明确的定义;

解决方法:采用singleton设计模式,将每个non-local static对象搬到自己的专属函数内(该对象在函数内被声明为static),然后然后函数返回一个引用指向这个static对象,然后使用者调用这些函数,而不直接去指涉这些对象。这个方法的好处在于:C++保证了在函数内的local static对象会在“这个函数调用期间”“首次遇上该对象定义式时”被初始化;代码如下:

class filesystem

{

public:std:size_t numberdisks() const;

};

extern filesystem tfs;//修改为filesystem&  tfs(){staticfilesystem fs;return fs;}

class directory

{

public:directory(params) {std::size_t disks=tfs.numberdisks();//修改为  std::size_t disks=tfs().numberdisks;

};

directory tempdir(params);//修改为directory& tempdir() {static directory td; return td;}

修改之后,程序用户完全和以前一样使用,唯一不同的就是使用函数返回的是指向static对象的引用,而非static对象本身;

对于singleton模式下的reference-returning函数比较简单,往往可以变成inline函数,但是对于多线程环境下会带来很大的麻烦;

引申:编译单元是指产生单一目标文件的那些源码,基本上它是单一源码文件加上其所包含的头文件,平常写程序的一个文档就称为一个编译单元;

结论:为了避免在对象初始化之前使用对象,需要做三件事情:1)手工初始化内置类型non-number对象;2)使用成员初始值列表对方对象的所有成分;3)在初始化次序不确定的情况下可以考虑singleton设计模式,也就是在处理跨编译单元的初始化次序时,用local static对象替换non-local static对象。

5:如果自己没有声明类中的函数,编译器会自动生成一个default构造函数、一个copy构造函数、一个copy assignment操作符和一个析构函数(non-virtual),并且这些函数都是public和inline的;

编译器生成的copy构造函数和copy assignment操作符只是单纯地将来源对象的每一个non-static成员变量拷贝给目标对象;

如果自己声明了一个构造函数,则编译器不再提供default构造函数;

编译器生成的copy assignment操作符,行为和copy构造函数一样,当且仅当生成的代码合法且有意义时;否则编译器拒绝为class生成operator=,如成员变量中含有引用或者const变量时,则编译器不能为自动生成一个copy assignment操作符;

编译器拒绝自动生成一个copy assignment构造函数的情况:1)内含reference成员变量;2)内含const变量;3)在base classes将copy assignment操作符声明为private;编译器拒绝为derive classes生成一个copy assignment操作符;

6:如果想要阻止某些函数被创建出来,声明这个函数,并将其权限设置为private,但是member函数和friend函数还是可以调用private函数;

阻值member或者friend函数调用的方法,利用一个base class,将需要阻止的函数(private权限)放到base class内,我们所需要做的就是(private)继承base class;当我们的类要生成copy构造函数和copy assignment函数时,会调用base class类中的对应函数,这些调用会被编译器拒绝,因为函数的权限是private;

Effective C++学习第二天相关推荐

  1. Effective C++ 学习笔记 第七章:模板与泛型编程

    第一章见 Effective C++ 学习笔记 第一章:让自己习惯 C++ 第二章见 Effective C++ 学习笔记 第二章:构造.析构.赋值运算 第三章见 Effective C++ 学习笔记 ...

  2. 《Javascript入门学习全集》 Javascript学习第二季(实战4)

    Javascript学习第二季(实战4)   上章的例子虽然实现了功能,也做了相应的判断,也符合标准了.但还有一个问题就是: Choose an image. 在html中只是为了图片切换 而做的,而 ...

  3. 再发力!Facebook AI何恺明等最新研究MoCo(动量对比学习)第二版,超越Hinton的SimCLR,刷新SOTA准确率...

    关注上方"深度学习技术前沿",选择"星标公众号", 资源干货,第一时间送达! [导读]无监督学习再发力!Facebook AI 研究团队的陈鑫磊.樊昊棋.Ros ...

  4. jQuery框架学习第二天:jQuery中万能的选择器

    jQuery框架学习第一天:开始认识jQuery jQuery框架学习第二天:jQuery中万能的选择器 jQuery框架学习第三天:如何管理jQuery包装集 jQuery框架学习第四天:使用jQu ...

  5. React  学习第二天 2018-07-21

    React  学习第二天 我这个React 学习存在以下毛病 1.不报错, 2.不能自动热加载,不能自动刷新 3.不能修改props 属性的值,但是这个却能够修改. 1.Vue 和React的关于 k ...

  6. JavaScript学习 第二课(二)

    JavaScript学习 第二课(二) 一.Math对象: 该对象的作用是用来处理数学运算符的,该对象不需要手动创建,因为它是window对象的一个属性,当页面加载完毕后,后台就是自动创建Math对象 ...

  7. 大一java怎么学好_是否应该学习第二门语言,学那个比较合适。

    如果从尽快找工作的角度,我认为不需要学习第二门语言.计算机语言只是工具!尽快用自己已经掌握的语言向计算机世界更重要的问题进发,完成项目更重要.比如你说的Java Web.因为这将让你了解更多计算机世界 ...

  8. 深入理解吴恩达老师深度学习课程(01神经网络和深度学习 第二周)

    深入理解吴恩达深度学习(01神经网络和深度学习 第二周) 1引言 2.1 二分类(Binary Classification) 2.1.1 符号定义(视频给出的) 2.2 逻辑回归(Logistic ...

  9. Python小白学习第二天

    Python学习第二天 今日学习:二进制与字符编码.保留字.变量定义.数据类型.数据转换 学习内容: 二进制与字符编码 #二进制与字符编码 print(chr(0b100111001011000)) ...

最新文章

  1. Ubuntu中使用WPS
  2. 【编程1】 Two Sum + 哈希算法
  3. 数据结构(一)---顺序表的实现---java版
  4. java 输出编码_从代码看java输入输出中的编码和解码
  5. python中x 1什么意思_Python:A [1:]中x的含义是什么?
  6. 个人博客前端模板_腾讯前端开发工程师,教你极速搭建一个个人博客网站
  7. 决策树(西瓜书学习)
  8. 腾讯云对象存储 python_GitHub - fushall1104/cos-python3-sdk: 腾讯云对象存储服务(cos)Python3.5版本SDK...
  9. springboot统一封装返回结果
  10. 大剧院自助签证_剧院集团通过像开放组织一样取得成功
  11. Java读 写文本_java读文件写文件的方法
  12. 怎么用eclipse编写python_python用eclipse开发配置
  13. java蓝牙开发_Android蓝牙开发全面总结
  14. 计算机作业word电子杂志,怎么用Word文档制作电子杂志目录
  15. 二开免签支付修复版系统源码带YY通道
  16. Dynamic Head: Unifying Object Detection Heads with Attentions论文阅读
  17. Cobbler 自动装机系统
  18. Excel Vba快速界面设计入门
  19. 360需要的,不是打工者——周鸿祎在360新员工入职培训上的讲话
  20. 看网页视频如何自定义倍速(b站举例)

热门文章

  1. 动态规划(0-1背包)--- 改变一组数的正负号使得它们的和为一给定数
  2. Azure IoT Hub和Event Hub相关的技术系列-索引篇
  3. 【C++】满二叉树问题
  4. NFS网络共享文件系统
  5. EasyRMS录播管理服务器项目实战:windows上开机自启动NodeJS服务
  6. 【UVA 10816】 Travel in Desert (最小瓶颈树+最短路)
  7. lr_start_timer,lr_get_transaction_duration,lr_get_transaction_wasted_time函数使用总结
  8. 如何更改Visual Studio 2008中类文件引用的默认名称空间?
  9. 孩子在华艺舞校的画画投稿-天女之梦
  10. [导入]一再的变故,终于决定何去何从.