基类为B,派生类为C,直接上代码以及运行结果。
目录
思路分析
代码一
运行结果一
代码二:B(i)改为b(i)
运行结果二
代码三:加上B(i)
运行结果三
代码四:删掉C类定义的B对象b,删除b(i)
运行结果四
思路分析
经评论区提醒,5月13日补充思路:首先,要知道基类和派生类的构造函数执行顺序是先执行基类的构造函数,再执行派生类的构造函数;而析构函数的执行顺序与构造函数的执行顺序刚好相反。
其次,如果在派生类的构造函数中显式指定了调用基类的哪个构造函数,就会先执行这个构造函数;如果没有指定,则会调用基类的默认构造函数。
最后要注意的是,代码中的派生类C,除了继承一个基类B的整型变量b之外,还自定义了一个基类B的对象b,而这个对象b还包括了一个整型变量b,这三个b要注意区分。
为了方便,我们称B类的b变量为b1,C类的b对象的b变量为b2。
代码一中,由于C的构造函数显示指定了调用B的带参数的构造函数,所以会先输出“B`s constructor called.”,此时b1=i=5;然后由于C中定义的B类对象b并没有指定构造函数,所以会调用B类默认的构造函数,输出“B`s default constructor called.”,此时b2=0;然后调用C的带参构造函数,输出“C`s default constructor called.”,同时使得c的值为6;然后执行C类的Print函数,先执行B类的Print函数,输出b1的值为5,再输出c的值为6。最后按照与执行构造函数相反的顺序执行析构函数。
代码二中,由于将B(i)改成了b(i),显示指定了C类的b对象调用的构造函数,而基类B调用哪个构造函数并没有被指定,因此先调用B类的默认构造函数,使得b1=0;然后调用C类的b对象的带参数的构造函数,使得b2=5;然后调用C的带参构造函数,同时使得c的值为6;然后执行C类的Print函数,先输出b1的值0,再输出c的值6;最后按照与执行构造函数相反的顺序执行析构函数。
代码三中,由于加上了B(i),因此会先显示调用基类B的带参构造函数,再显示调用C类b对象的带参数的构造函数,使得b1=5,b2=5;然后调用C的带参构造函数,同时使得c的值为6;C类的Print函数先输出b1的值5,再输出c的值6;最后按照与执行构造函数相反的顺序执行析构函数。
代码四中,删掉C类定义的B对象b,删除b(i),因此只会显示调用基类B的带参构造函数,使得b1的值为5;然后调用C的带参构造函数,同时使得c的值为6;C的Print函数会先输出b1的值5,再输出c的值6;最后按照与执行构造函数相反顺序执行析构函数。
代码一
#include <iostream>
using namespace std;
class B{
public:
B();
B(int i);
~B();
virtual void Print();
private:
int b;
};
B::B(){
b=0;
cout<<"B`s default constructor called."<<endl;
}
B::B(int i){
b=i;
cout<<"B`s constructor called."<<endl;
}
B::~B(){
cout<<"B`s destructor called."<<endl;
}
void B::Print(){
cout<<b<<endl;
}
class C:public B{
public:
C();
C(int i,int j);
~C();
void Print();
private:
int c;
B b;
};
C::C(){
c=0;
cout<<"C`s default constructor called."<<endl;
}
C::C(int i,int j):B(i){
c=j;
cout<<"C`s constructor called."<<endl;
}
C::~C(){
cout<<"C`s destructor called."<<endl;
}
void C::Print(){
B::Print();
cout<<c<<endl;
}
int main()
{
C obj(5,6);
obj.Print();
return 0;
}
运行结果一
代码二:B(i)改为b(i)
#include <iostream>
using namespace std;
class B{
public:
B();
B(int i);
~B();
virtual void Print();
private:
int b;
};
B::B(){
b=0;
cout<<"B`s default constructor called."<<endl;
}
B::B(int i){
b=i;
cout<<"B`s constructor called."<<endl;
}
B::~B(){
cout<<"B`s destructor called."<<endl;
}
void B::Print(){
cout<<b<<endl;
}
class C:public B{
public:
C();
C(int i,int j);
~C();
void Print();
private:
int c;
B b;
};
C::C(){
c=0;
cout<<"C`s default constructor called."<<endl;
}
C::C(int i,int j):b(i){
c=j;
cout<<"C`s constructor called."<<endl;
}
C::~C(){
cout<<"C`s destructor called."<<endl;
}
void C::Print(){
B::Print();
cout<<c<<endl;
}
int main()
{
C obj(5,6);
obj.Print();
return 0;
}
运行结果二
代码三:加上B(i)
#include <iostream>
using namespace std;
class B{
public:
B();
B(int i);
~B();
virtual void Print();
private:
int b;
};
B::B(){
b=0;
cout<<"B`s default constructor called."<<endl;
}
B::B(int i){
b=i;
cout<<"B`s constructor called."<<endl;
}
B::~B(){
cout<<"B`s destructor called."<<endl;
}
void B::Print(){
cout<<b<<endl;
}
class C:public B{
public:
C();
C(int i,int j);
~C();
void Print();
private:
int c;
B b;
};
C::C(){
c=0;
cout<<"C`s default constructor called."<<endl;
}
C::C(int i,int j):B(i),b(i){
c=j;
cout<<"C`s constructor called."<<endl;
}
C::~C(){
cout<<"C`s destructor called."<<endl;
}
void C::Print(){
B::Print();
cout<<c<<endl;
}
int main()
{
C obj(5,6);
obj.Print();
return 0;
}
运行结果三
代码四:删掉C类定义的B对象b,删除b(i)
#include <iostream>
using namespace std;
class B{
public:
B();
B(int i);
~B();
virtual void Print();
private:
int b;
};
B::B(){
b=0;
cout<<"B`s default constructor called."<<endl;
}
B::B(int i){
b=i;
cout<<"B`s constructor called."<<endl;
}
B::~B(){
cout<<"B`s destructor called."<<endl;
}
void B::Print(){
cout<<b<<endl;
}
class C:public B{
public:
C();
C(int i,int j);
~C();
void Print();
private:
int c;
};
C::C(){
c=0;
cout<<"C`s default constructor called."<<endl;
}
C::C(int i,int j):B(i){
c=j;
cout<<"C`s constructor called."<<endl;
}
C::~C(){
cout<<"C`s destructor called."<<endl;
}
void C::Print(){
B::Print();
cout<<c<<endl;
}
int main()
{
C obj(5,6);
obj.Print();
return 0;
}