gpt4 book ai didi

c++ - 派生类中基类的成员变量初始化顺序(构造函数)

转载 作者:行者123 更新时间:2023-11-28 01:52:24 31 4
gpt4 key购买 nike

我是否正确理解了这里的初始化工作原理?我将说明步骤:

  1. 基类构造函数被调用。我们输出 0并增加 m_i = 1 ;
  2. m_xm_a 之前在基类的成员变量中,我们正在预递增m_i .我们输出 2然后我们增加 m_i .
  3. 我们正在为 m_a[0] 创建一个 A 类型对象的动态数组。我们输出 0然后我们增加 m_i ;对于 m_a[1] 我们输出 0然后我们增加 m_i . m_i对于 m_a[0]等于1m_i对于 m_a[1]等于1 .
  4. 最后我们转到派生类构造函数的主体,我们输出 m_i = 2.

the output is : 02002

我真的不明白为什么 m_i 的输出当我们进入基本构造函数的主体时等于 2?不应该m_i等于3在第 2 步之后?


源代码

   #include <iostream>

class A
{
public:
A(int n = 0)
: m_i(n)
{
std::cout << m_i;
++m_i;
}

protected:
int m_i;
};

class B
: public A
{
public:
B(int n = 5) : m_a(new A[2]), m_x(++m_i){ std::cout << m_i; }

~B() { delete [] m_a;}

private:
A m_x;
A *m_a;

};

int main()
{
B b;
std::cout << std::endl;

return 0;
}

最佳答案

在我解释这个问题之前,让我这样说:如果你的对象的初始化非常复杂以至于它需要我将要涉及的详细知识,那么修复那个。使初始化过于复杂对任何人都没有好处。

现在,让我们看看当您通过调用其默认构造函数来构造 B 类型的对象时会发生什么。

由于B::A 没有在成员初始化器列表中提及,它将被默认初始化。这将使用其默认值 0 调用 A(int)。其结果将使用值 0 初始化 B::A::m_i,然后输出该值,然后将 B::A::m_i 递增到值 1。

现在,我们初始化B的成员。第一个要初始化的成员是 B::m_x。此成员初始化程序读取并递增 B::A::m_i 的值,这是一个有效的初始化值,在此操作之前恰好为 1。因此,在为 B::m_x 调用 A(int) 之前,B::A::m_i 取值 2。

B::m_x 通过调用值为 2 的 A(int) 进行初始化。它将该值存储在 B::m_x.m_i 中,将其输出,并将其递增 1。

接下来,我们初始化B::m_a。成员初始化器通过调用 new A[2] 对其进行初始化,这将默认构造 A 的 2 个实例。这些都与您的问题完全无关,因为它们与 B::A::m_i 没有任何关系。但它确实输出了两个零。

初始化B::m_a后,我们进入B的默认构造函数本身。在那里,它只是输出B::A::的值。 m_i。如果您还记得的话,最后设置为 2。这就是它的输出。

关于c++ - 派生类中基类的成员变量初始化顺序(构造函数),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42474518/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com