class base {
public:
base(){
cout << "base constructor" << endl;
}
base(const base& rh) {
cout << "base copy constructor" << endl;
}
};
//case 1:
class der : public base {
};
//case 2:
class der : public base {
public:
der(){
cout << "der constructor" << endl;
}
der(const der& rh) {
cout << "der copy constructor" << endl;
}
};
int main() {
der d;
der d1(d);
}
案例1:der d1(d);调用基类复制构造函数,而在
中case-2,基类默认构造函数和der类复制构造函数 被调用。
任何人都可以解释这个逻辑吗?
答案 0 :(得分:3)
在案例1中,您将获得编译器合成的默认复制构造函数。这被定义为复制基础和成员。
在第2种情况下,您定义了自己的复制构造函数,它会执行您要求它执行的操作。您没有在基类的初始化列表中放置任何内容,因此基类是default-construct [*],与未显式初始化基类的任何其他构造函数相同。如果der
有任何数据成员,则不会复制这些成员。
[*]或其他一种初始化,对于非POD类来说是相同的。我永远记不起那些细节。
答案 1 :(得分:2)
默认情况下,派生副本构造函数不会调用基类复制构造函数。如果不告诉派生类复制构造函数调用基类复制构造函数,它仍然需要构造基础子对象,因此它必须调用基本的默认构造函数。
但是在下面的示例中,您将看到可以在派生类的成员initilize列表中添加对基本复制构造函数的调用:
class base {
public:
base(int i):m_i(i){
cout << "base constructor" << endl;
}
base(const base& rh) {
m_i = rh.m_i;
cout << "base copy constructor" << endl;
}
private:
int m_i;
};
//case 2:
class der : public base {
public:
der(int i,int j):base(i),m_j(j){
cout << "der constructor" << endl;
}
der(const der& rh):base(rh) {
m_j = rh.m_j;
cout << "der copy constructor" << endl;
}
private:
int m_j;
};
int main() {
der d(1,2);
der d1(d); //d1.m_i = 1, d1.m_j = 2
}
//result
//base copy constructor
//der copy constructor
答案 2 :(得分:0)
在第一种情况下,您没有为der
指定构造函数,因此编译器会为您决定,即将d
的数据单独复制到d1
,调用复制构造函数base
正在进行中。
在第二种情况下,您已指定了复制构造函数,您不会自己调用base
的复制构造函数。由于您已经覆盖了der
的复制构造函数(它告诉编译器执行您所说的,而不是它想要的),编译器不能假设您想要来调用{的复制构造函数{1}}也是。
答案 3 :(得分:0)
基本上是调用一个copy-con。所以在case-2中调用der的copy-con,如果你愿意,你可以在代码中使用base的copy-con。在第一种情况下,因为你没有实现copy-con,所以它从他的base调用函数,就像它只对基类中实现的任何函数一样。