effective C++ 04_确定对象被使用前已被初始化 读书笔记

来源:互联网 发布:山东大学怎么样知乎 编辑:程序博客网 时间:2024/06/01 21:18

1.读取未初始化的值会导致不明确行为。
2.C part of C++不保证发生初始化,一旦进入non-C parts of C++, 规则有些变化(我个人理解,会保证初始化)。这就很好的解释了为什么array(来自C part of C++)不保证其内容被初始化,而vector(来自STL part of C++)却有此保证。
这里我看到过array创建以后,立马就用memset初始化为0的。 但是vector就不用。 所以我自己的话,还是优先使用string和vector,这样可以减少犯错的机会。
3.作者推荐构造函数的一个较佳写法是,使用所谓的member initalization list(成员初值列)替换赋值动作:
ABEntry:ABEntry(const std::string& name, const std::string& address, const std::list& phones)
:theName(name),theAddress(address),thePhones(phones),numTimesConsulted(0) //现在,这些都是初始化
{} //现在,构造函数本体不必有任何动作

对已自定义的class类型,使用成员初值列,可以提高效率。 对于内置类型(C语言的老类型),在构造函数或者成员初值列里赋值效率是一样的。 所以可以使用一个private的init函数,把内置类型的赋值都放在init中, 这样如果有多个构造函数的重载,就可以在构造函数本体里面调用init函数,来避免代码重复。 不过对自定义的class类型,还是有必要使用初值列。
如果成员变量是const或者references,即使是内置类型,也必须在成员初值列中初始化。 因为const或者references不能赋值, 在成员初值列中叫初始化,如果在构造函数本体里面,叫赋值,因为调用到构造函数本体时,已经初始化完了,对象已经生成,本体里面是赋值,再次改变了对象的成员变量的值。
4.关于初始化次序,base classes更早于其derived classes被初始化,而class的成员变量总是以其声明次序被初始化。即使它们在成员初值列中以不同的次序出现(很不幸那是合法的),也不会有任何影响。 作者推荐成员初值列次序按照声明次序为次序。
5.为免除”跨编译单元之初始化次序”问题,请以local static对象替换non-local对象。 这个同时也是单例模式的C++的一种写法。
class FileSystem {…};
FileSystem& tfs()
{
static FileSystem fs;
return fs; //注意,返回的是该对象的一个reference
}
如果你从未调用过此函数,就不会引发构造和析构成本。 这个手法的基础在于:C++ 保证,函数内的local static 对象会在”该函数被调用期间”“首次遇上该对象之定义式”时被初始化。

阅读全文
0 0
原创粉丝点击