[说明] 本文是根据Herb Sutter的《More Exceptional C++》条款36的精简翻译笔记,不明之处,参考原文。
1、直接初始化:使用单个构造函数(可能是转换构造函数)来初始化对象,形式如“T t(u)”。
2、拷贝初始化:使用拷贝构造函数来初始化对象,有必要的话会在此之前,先调用一个用户自定义的类型转换,形式如“T t=u”。
注意:一般而言,在变量初始化时,尽量采用直接初始化形式,而不是拷贝初始化。
3、分析下例中采用的初始化形式。
class T : public S {
public:
T() : S(1), x(2) {} //基类初始化与成员初始化
X x;
};
//////答案:基类与成员的初始化兜采用的是直接初始化。////////
T f( T t) { return t; } //传递函数参数与返回值
/////答案:值的传递与返回都是采用的拷贝初始化。////////
S s;
T t;
S& r = t;
reinterpret_cast< S& > (t);
dynamic_cast< T& > (r);
const_cast< const T& > (t);
//////答案:以上各种转换并没有涉及到新对象的产生,只是创建了引用而已。/////////
static_cast< S > (t);
///////答案:static_cast采用直接初始化。//////////
try { throw T(); } //抛出异常
catch (T t) {} //处理异常
//////答案:异常对象的抛出与捕获都采用拷贝初始化。////////
f( T(s) ); //函数风格的类型转换采用的是直接初始化
S a[3] = {1, 2, 3}; //大括号初始化语句采用的是拷贝初始化
S* p = new S(6); //new表达式采用的是直接初始化