我有一个声明和定义构造函数的基类,但由于某种原因,我公开派生的类没有看到那个构造函数,因此我必须在派生类中显式声明转发构造函数:
class WireCount0 {
protected:
int m;
public:
WireCount0(const int& rhs) { m = rhs; }
};
class WireCount1 : public WireCount0 {};
class WireCount2 : public WireCount0 {
public:
WireCount2(const int& rhs) : WireCount0(rhs) {}
};
int dummy(int argc, char* argv[]) {
WireCount0 wireCount0(100);
WireCount1 wireCount1(100);
WireCount2 wireCount2(100);
return 0;
}
在上面的代码中,我的WireCount1 wireCount1(100)
声明被编译器拒绝(“没有匹配的函数用于调用'WireCount1 :: WireCount1(int)'”),而我的wireCount0
和{{ 1}}声明很好。
我不确定我理解为什么需要提供wireCount2
中显示的显式构造函数。是因为编译器为WireCount2
生成了默认构造函数,并且该构造函数隐藏了WireCount1
构造函数?
作为参考,编译器为WireCount0
。
答案 0 :(得分:14)
构造函数不是继承的。您必须为派生类创建构造函数。此外,派生类的构造函数必须调用基类的构造函数。
答案 1 :(得分:6)
所有派生类必须以某种形式或形式调用其基类的构造函数。
当您创建重载的构造函数时,您的默认编译器生成的无参数构造函数将消失,派生类必须调用重载的构造函数。
当你有这样的事情时:
class Class0 {
}
class Class1 : public Class0 {
}
编译器实际上生成了这个:
class Class0 {
public:
Class0(){}
}
class Class1 : public Class0 {
Class1() : Class0(){}
}
如果有非默认构造函数,则不再生成无参数构造函数。定义以下内容时:
class Class0 {
public:
Class0(int param){}
}
class Class1 : public Class0 {
}
编译器不再在Class1中生成构造函数来调用基类的构造函数,您必须自己明确地这样做。
答案 2 :(得分:1)
在处理派生之前,你必须构造你的基类。如果使用非平凡的构造函数构造派生类,编译器就无法决定调用base的内容,这就是发生错误的原因。