简体   繁体   English

父类中的构造方法不会将值分配给私有变量

[英]Constructor in the parent class doesn't assign the value to a private variable

This is my code and you can also run it from http://cpp.sh/5lsds 这是我的代码,您也可以从http://cpp.sh/5lsds运行它

#include "iostream"
using namespace std;
class X{
private:
    int c;
public:
    X(){}
    X(int b){
    c = 11;
    }
    int getC();
};
class Z:public X{
public:
    Z(int n){
        X(23);
    }
};
int main()
{
    Z z(1);
    cout<<z.getC()<<endl;
    return 0; 
}
int X::getC(){
    return c;
}

I need to have X(){} line since the child constructor needs to call the parent default constructor. 我需要X(){}行,因为子构造函数需要调用父默认构造函数。

If you run the program from http://cpp.sh/5lsds you can see that the output is 0 while I expect it to be 11 . 如果从http://cpp.sh/5lsds运行该程序,则可以看到输出为0而我希望它为11 Since the Z constructor calls X constructor with an int parameter and it sets the c value to 11 but the output is 0 . 由于Z构造函数使用int参数调用X构造函数,并且将c值设置为11但输出为0

You should use member initializer list , 您应该使用成员初始值设定项列表

In the definition of a constructor of a class, member initializer list specifies the initializers for direct and virtual base subobjects and non-static data members. 在类的构造函数的定义中,成员初始化程序列表指定直接和虚拟基础子对象以及非静态数据成员的初始化程序。

eg 例如

Z(int n) : X(23) {}

I need to have X(){} line since the child constructor needs to call the parent default constructor. 我需要X(){}行,因为子构造函数需要调用父默认构造函数。

With member intializer list it's not required again (in this code sample). 使用成员初始化器列表,不再需要它(在此代码示例中)。

For X(23); 对于X(23); in the body of the constructor, you're just creating a temporary X , which has nothing to do with the base subobject X of Z ; 在构造函数的主体中,您只是创建一个临时X ,它与Z的基础子对象X无关; Then the default constructor of X (ie X::X() ) will be used for it. 然后将使用X的默认构造函数(即X::X() )。 ie it's equivalent with: 即它等效于:

Z(int n) : X() {  // initialize the base suboject X via X::X()
    X(23);        // create an unnamed temporary via X::X(int)
}

You don't invoke the constructor of the base class 您不调用基类的构造函数

Z(int n){
    X(23);
}

This creates an unnamed temporary X object, and passes 23 to its constructor. 这将创建一个未命名的临时X对象,并将23传递给其构造函数。 It doesn't construct the X sub-object of Z. 它不会构造Z的X子对象。

In C++, we construct bases and members using the member initializer list syntax: 在C ++中,我们使用成员初始化器列表语法构造基和成员:

X(int b) :
  c(11)
{}

Z(int n) :
  X(23)
{}

The member initializer list syntax is pretty much equivalent to the assignment you do when a simple integer is the constructed member. 成员初始化器列表的语法与构造一个简单整数时的赋值等效。 But beware that more complex sub-objects will be default constructed first, and then have their assignment operator invoked. 但是请注意,将首先默认构造更复杂的子对象,然后再调用它们的赋值运算符。 That could make a substantial (worsening) difference in performance to just specifying them in the member initializer list and constructing once. 仅在成员初始化器列表中指定它们并构造一次,就可能在性能上产生巨大的(令人担忧的)差异。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM