C++进阶之二:《C++高级编程》掌握类和对象 阅读笔记

C++  ㅜㅔㅇㅇㅜstudy notice

Chap 8 掌握类与对象

1.     智能指针 Smart  pointer:

auto myCellp = make_unique<SpreadshettCell>();

// or

// unique_ptr<SpreadsheetCell> myCellp(new SpreadsheetCell());

2.     默认构造函数 default  constructor

Class SpreadsheetCell {

Public:

SpreadsheetCell() = default ; // explicitly defaulted constructor)

// or

SpreadsheetCell() = delete; // explicitly deleted constructors)

只要在类中动态分配类内存,就应该编写析构函数、复制构造函数和赋值运算符;

如果不需要上面的函数,可以参考下面的方式禁止掉:

SpreadSheet(const SpreadSheet & src) = delete;

SpreadSheet & operator=(const SpreadSheet & rhs) = delete;

3.     ctor-initializer和构造函数

ctor-initializer  differs from inner construction in Construct function:

ctor-initializer will create new object and change its value during constructing; and the initialization order should follower the member’s declared order;

构造函数只能修改成员变量的值,成员变量的默认构造函数可以初始化成员,但是对没有默认构造函数的成员就没有办法初始化类。就得交给ctor-initializer去处理,因为ctor-initializer 能比构造函数更早地执行。

 

哪些数据成员必须在ctor-initializer中进行初始化:

数据类型

说明

Const 数据成员

因为const数据成员创建之后就没有机会再修改类,必须在创建的时候提供值

引用数据成员

如果不指定一个值,引用就无法存在

没有默认构造函数的对象数据成员

C++尝试用默认构造函数初始化成员对象,如果不存在默认构造函数,就无法初始化这个对象

没有默认构造函数的基类

具有基类的对象创建时会执行基类的默认构造函数,除非在   ctor-initializer中调用类了基类构造函数,此时调用这个构造函数,而不是默认构造函

 

4. if any constructor function is declared, default constructor won’t be generated;

值传递默认会用到拷贝构造函数:value transfer mode means the copy-constructor method:

use const & to transfer read-only parameter rather than copy-replicate parameter functins;

5. C++ 11 and later version support In-Class Member Initializer

6. virtual/static/ 只需出现在方法的声明的时候,在定义的时候无需重复出现

7.类声明时候已经定义的函数,会被编译器当成内联函数,内联函数需要都在头8.文件中定义,但只是建议编译器进行优化。最好优化与否,取决于编译器。

枚举类:

 enum class Colors {Red =1, Green, Blue, Yello};

9.const 对象可以调用过const方法和非const方法。然而,const对象只能调用const方法;不能将静态方法声明为const, 因为静态方法没有类的实例,不可能改变某个对象内部的值,因此把static方法声明为const是多余的。

10. mutable 数据成员

改变类对象的数据成员,但是这个改动对用户可见的数据没有任何影响,但在技术上确实做了改动,因此编译器不允许将它声明为const, 在这种情况下可以声明为mutable数据成员。例如统计访问某个数据成员频率的成员函数:

 

double SheetCell:: getValue() const {

            mNumAccess++;

return mValue;

}

 

void SheetCell:setValue(int val) {

            mNumAccess++;

mValue = val;

}

10.创建稳定的接口

使用接口类和实现内:

接口内:对外,只改变某个类的的时候,如果这个类实现类接口和实现的分离,可以极大地缩短编译时间,因为只需要重新编译实现类;

std::unique_ptr 类型的数据成员不运行直接被赋值;

 

chap 9  揭秘继承技术

只有在基类中声明为virtual的方法才能被派生类正确地重写,virtual关键字出现在方法方法声明的开头。

为类防止重写方法是否可以运行的担心,最好把所有的方法声明为virtual,这样的代价是稍微对性能有些影响。(为啥?)

 chap 9.2

如何修改基类中的方法:

对应的方法在基类和派生类中都需要virtual 字段修饰;

对应的方法在派生类中声明的时候,需要加上override后缀;

chap 9.3 利用父类

chap 9.3.1

对象的创建顺序:

如果具有父类,就首先执行父类的默认构造函数;除非在 ctor-initializer中调用类了基类构造函数,此时调用这个构造函数,而不是默认构造函数;

类的非静态数据成员按照声明的顺序创建;

执行改类的构造函数;


猜你喜欢

转载自blog.51cto.com/xiamachao/2283301