C++初始化列表和内存分配

leg*_*s2k 4 c++ constructor memory-management smart-pointers initialization-list

以下是否有效?

class myClass
{
   private:
     ...
     int m_nDataLength;
     boost::shared_array<int> m_pData;
     ...

   public:
     myClass(): ..., m_nDataLength(10), m_pData(new int[m_nDataLength]), ...
     {
     }
}
Run Code Online (Sandbox Code Playgroud)

我是否正确地假设初始化将完全按照我在ctor中给出的顺序发生?如果没有,如果在m_pData之后m_nDataLength的初始化发生了怎么办?

sbi*_*sbi 10

虽然您的示例中的初始化确实按您想要的顺序发生,但这并不是您假设的原因:初始化按类定义中的数据成员声明的顺序发生.这样做的原因是析构函数必须以向后的顺序销毁成员,而不管使用哪个构造函数来创建对象.为此,必须使用与构造函数无关的定义构造顺序的方法.

这意味着,如果不是

class myClass
{
   private:
     ...
     int m_nDataLength;
     boost::shared_array<int> m_pData;
Run Code Online (Sandbox Code Playgroud)

有人会将你的代码更改为

class myClass
{
   private:
     ...
     boost::shared_array<int> m_pData;
     int m_nDataLength;
Run Code Online (Sandbox Code Playgroud)

然后代码会有一个bug.

我的建议是:

  • 编写构造函数,以便初始化顺序无关紧要.
  • 如果你不能这样做(注意:对我来说,这在过去十年中发生的次数不到5次),请在声明数据成员时明确说明.

这样的事情应该做:

class myClass
{
   private:
     ...
     int m_nDataLength;                 // Note: Declaration order
     boost::shared_array<int> m_pData;  //       matters here!
Run Code Online (Sandbox Code Playgroud)


not*_*row 9

初始化将按类中的顺序初始化字段,因此:如果更改

private:
  ...
  int m_nDataLength;
  boost::shared_array<int> m_pData;
Run Code Online (Sandbox Code Playgroud)

private:
  ...
  boost::shared_array<int> m_pData;
  int m_nDataLength;
Run Code Online (Sandbox Code Playgroud)

它不会工作.在构造函数中,订单不适用.


CB *_*ley 5

不,类成员的初始化按成员出现在类定义中的顺序发生.如果成员出现在初始化列表中,那么它控制用于初始化该成员的表达式(即使它使用尚未初始化的成员),但它在初始化列表中出现的位置不会影响初始化时间.