条款1 视C++为一个语言联邦
没啥好说的
条款2 尽量以const, enum, inline替换#define
宏定义的变量可能不会进入符号表(symbol table)
在define
之后,可能在运用该常量的过程中获得一个编译错误,这个错误也许会提到定义的结果,而不会提到那个常量的名字,这样会导致困惑,因为需要追踪那个常量就显得十分困难。
const
定义的语言常量肯定会被编译器看到,因此会进入符号表
宏定义无法创建class专属常量
#define 不重视作用域
一旦宏被定义,就在其后的变异过程中有效 所以#define也没有封装性
一个属于枚举类型的数值可以充当int使用
#class GamePlayer{
private:
enum{NumTurns=5};
int scores[NumTurns];
};
对于形如函数的宏,最好用inline函数替换#define
现代编译器会自动inline,而不是根据编写代码者是否添加inline来判断
条款3 尽可能使用const
T* const
指针不得指向不同东西
const T*_ _
和 T const*
指针指向的东西不可变动
class的const成员函数可以操作const对象
如果函数返回类型是内置类型,那么改动函数返回值不合法 对返回值的改动必须要求函数返回值是左值引用
const成员函数可以使用类的成员,但不能修改任何 non-static 成员变量
类的const成员变量(常量)只能通过构造函数的初始化列表
条款4 确定对象被使用前已被初始化
在使用前确保初始化
构造函数一定要用member initialization list进行构造 而不是对于每个成员挨个赋值
原因在于 基于赋值的版本会先调用default构造函数对成员进行默认初始化,然后再调用这个版本的构造函数进行赋值动作的初始化
效率远远不如member initialization list的构造
如果成员变量是const或reference,就一定需要初值,不能被赋值
C++有十分固定的成员初始化次序,class的成员变量总是以其声明次序被初始化,不论它们在构造函数中的顺序是什么样的 但是最好按照声明顺序进行初始化
Singleton模式:
C++在多单元编译的时候 编译顺序具有不确定性 以local static对象 替换non-local static对象 这部分注意看原书