在没有默认构造函数的情况下创建的派生对象

Derived object created without having default constructor

本文关键字:情况下 创建 派生 对象 构造函数 默认      更新时间:2023-10-16

我正在一个站点上做一个小测试,我遇到了这个问题。

#include<iostream.h> 
class Base
{
int x, y, z; 
public: 
Base()
{
x = y = z = 0;
}
Base(int xx, int yy = 'A', int zz = 'B')
{
x = xx;
y = x + yy;
z = x + y;
}
void Display(void)
{
cout<< x << " " << y << " " << z << endl;
}
};
class Derived : public Base
{
int x, y; 
public:
Derived(int xx = 65, int yy = 66) : Base(xx, yy)
{
y = xx; 
x = yy;
}
void Display(void)
{
cout<< x << " " << y << " ";
Display(); 
}
};
int main()
{
Derived objD;
objD.Display();
return 0; 
}

我选择编译错误选项是因为我们正在实例化一个构造函数的参数为零的派生对象,并且我们已经定义了一个需要 2 个参数的对象。据我所知,如果我们自己定义一个构造函数,编译器不再提供默认的构造函数。我运行代码并且它编译正确。有人可以解释一下吗,这让我真的很困惑。

这是因为您的 c'tor 中有默认参数,这意味着如果您不传入参数,那么它将默认参数。构造函数可以处理 0、1 或 2 个参数。

如果更改:

Derived(int xx = 65, int yy = 66) : Base(xx, yy)

Derived(int xx, int yy) : Base(xx, yy)

那么你的编译将失败

此外

由于您的 c'tor 只能与一个参数一起使用,您可能希望使用explicit

explicit Derived(int xx = 65, int yy = 66) : Base(xx, yy)

这不允许在您不希望隐式转换时进行隐式转换。显式转换仍然是可能的。如果您删除默认值,那么您将不需要这样做,因为您的 c'tor只能采用 2 个参数。

Derived类 doeasn 没有无参数构造函数,但它有一个可以在没有参数的情况下调用的构造函数:对Derived::Derived()的调用被解析为默认参数值的Derived::Derived(65, 66)