使用c ++ 11标准,我可以通过两种方式初始化类成员:
class MyClass
{
private:
int a = 5;
};
或
class MyClass
{
private:
int a;
public:
MyClass()
{
a = 5;
}
};
这两种方法是出于任何原因都优于另一种方法,还是更多的个人风格选择?
答案 0 :(得分:3)
第二个例子是不初始化。
因此,在这两个例子中,第一个是初始化类成员的最佳方法。
传统的初始化方式如下:
class MyClass
{
private:
int a;
public:
MyClass()
: a(5)
{}
};
虽然我们现在有第一个示例中的内联初始化程序,但是从C ++ 11开始。
答案 1 :(得分:1)
This page from the Standard C++ Foundation表明,在其他条件相同的情况下,您应该更喜欢使用初始化列表。那就是:
体型
class Foo {
public:
Foo(int bar) : m_bar(bar) { }
private:
int m_bar;
};
在
class Foo {
public:
Foo(int bar) {
m_bar = bar;
}
private:
int m_bar;
};
他们的理由:
考虑以下构造函数初始化成员对象
x_
使用初始化列表:Fred::Fred() : x_(whatever) { }
。该 这样做的最大好处是提高了性能。对于 例如,如果表达式与成员的类型相同 变量x_
,构造任何表达式的结果 直接在x_
内 - 编译器不会单独创建。{1}} 宾语。即使类型不相同,编译器通常也是如此 能够使用初始化列表做得比使用更好 分配。构建构造函数的另一种(低效)方法是通过赋值, 例如:
Fred::Fred() { x_ = whatever; }
。在这种情况下表达式 无论是什么导致创建一个单独的临时对象,这个 临时对象传递给x_
对象的赋值运算符。 然后在;
处破坏该临时对象。那效率很低。好像这还不够糟糕,还有另一个效率低下的根源 在构造函数中使用赋值时:成员对象将获得 完全由其默认构造函数构造,这可能是 例如,分配一些默认的内存量或打开一些默认值 文件。如果不管表达的话,所有这些工作都可能是徒劳的 和/或赋值运算符使对象关闭该文件和/或 释放该内存(例如,如果默认构造函数未分配 足够大的内存池或打开错误的文件。)
结论:在所有其他条件相同的情况下,如果您的代码运行得更快 你使用初始化列表而不是赋值。
关于默认初始化(例如Foo(): m_bar(5) { }
)我也会使用初始化列表方法(或C ++ 11成员初始化方法),只是为了与上述指南保持一致。