Vector::Vector(const Vector& a) : elem{new double[sz]}, sz{a.sz}
{
for(int i = 0; i!= sz; ++i)
elem[i] = a.elem[i];
}
这里有趣的部分是 elem {new double [sz]} 来之前
sz{a.sz}
所以就是在
之前sz
已初始化。
但它并没有抛出任何错误,对吧?
有人可以告诉我有关标准中相应部分的内容,对内部工作的更深入了解,或者其他方式如何受到监管?
答案 0 :(得分:10)
初始化列表的重要之处在于成员不是按照它们在初始化列表中的出现顺序初始化,而是按类中的声明顺序初始化。
C ++标准版n3337 § 12.6.2 / 10初始化基础和成员
在非委托构造函数中,初始化继续进行 以下顺序:
- 首先,仅适用于派生程度最高的类(1.8)的构造函数, 虚拟基类按照它们出现在的顺序进行初始化 深度优先从左到右遍历有向无环图 基类,其中“从左到右”是出现的顺序 派生类base-specifier-list中的基类。
- 然后,直接基类按声明顺序初始化为 它们出现在base-specifier-list中(无论顺序如何 MEM-初始化)。
- 然后,按照它们的顺序初始化非静态数据成员 在类定义中声明(再次无论顺序如何 MEM-初始化)。
- 最后,执行构造函数体的复合语句。
[注:声明命令的目的是确保基础和 成员子对象以相反的顺序销毁 初始化。 - 结束说明]
(现在我将重复我的另一个答案,但我认为这不会伤害任何人)这很重要。请记住这一点,以避免错误,如
/* trying to allocate (possibly) very large block of memory
as a result of initializing a vector with
uninitialized integer: std::vector<int> v( N)
*/
class SearchEngine {
std::vector<int> v;
int N;
explicit SearchEngine( std::vector<int> const& keys)
: N( keys.size()), v( N), {