继承构造函数的执行顺序

转自:http://blog.csdn.net/daheiantian/article/details/6438782

Code:

#include <iostream>
using namespace std;

class A {
public:
A() {
cout<<"int A::A()"<<endl;
}
A(A &a) {
cout<<"int A::A(A &a)"<<endl;
}
A& operator=(A& a) {
cout<<"int A::operator=(A &a)"<<endl;
return a;
}
virtual ~A() {
cout<<"int A::~A()"<<endl;
}
};

class M :public A {
public:
M() {
cout<<"int M::M()"<<endl;
}
M(M &a) {
cout<<"int M::M(M &a)"<<endl;
}
M& operator=(M& m) {
cout<<"int M::operator=(M &a)"<<endl;
return m;
}
virtual ~M() {
cout<<"int M::~M()"<<endl;
}
};

class B:virtual public M {
public:
B() {
cout<<"int B::B()"<<endl;
}
B(B &a) {
cout<<"int B::B(B &a)"<<endl;
}
B& operator=(B& b) {
cout<<"int B::operator=(B &a)"<<endl;
return b;
}
virtual ~B() {
cout<<"int B::~B()"<<endl;
}

};

class N :public A {
public:
N() {
cout<<"int N::N()"<<endl;
}
N(N &a) {
cout<<"int N::N(N &a)"<<endl;
}
N& operator=(N& n) {
cout<<"int N::operator=(N &a)"<<endl;
return n;
}
virtual ~N() {
cout<<"int N::~N()"<<endl;
}
};
class C:virtual public N {
public:
C() {
cout<<"int C::C()"<<endl;
}
C(C &a) {
cout<<"int C::C(C &a)"<<endl;
}
C& operator=(C& c) {
cout<<"int C::operator=(C &a)"<<endl;
return c;
}
virtual ~C() {
cout<<"int C::~C()"<<endl;
}
};
class E:virtual public M{
public:
E() {
cout<<"int E::E()"<<endl;
}
E(E &a) {
cout<<"int E::E(E &a)"<<endl;
}
E& operator=(E& e) {
cout<<"int E::operator=(E &a)"<<endl;
return e;
}
virtual ~E() {
cout<<"int E::~E()"<<endl;
}
};
class D:public B, public C, public E {
public:
D() {
cout<<"int D::D()"<<endl;
}
D(D &a) {
cout<<"int D::D(D &a)"<<endl;
}
D& operator=(D& d) {
cout<<"int D::operator=(D &a)"<<endl;
return d;
}
virtual ~D() {
cout<<"int D::~D()"<<endl;
}
};

int main(int argc, char **argv) {
cout<<"-------构造函数-------"<<endl;
D d;
cout<<"-------复制构造函数-------"<<endl;
D d1(d);
cout<<"-------赋值操作符-------"<<endl;
d = d1;
cout<<"-------析构函数-------"<<endl;

return 0;
}

Result:

-------构造函数-------
int A::A()
int M::M()//构造虚基类M时,要先构造其父类A
int A::A()
int N::N()//和M一样,构造虚基类N时,也要先构造其父类A
int B::B()//构造完虚基类,开始构造直接父类,按照声明顺序为B、C、E
int C::C()
int E::E()
int D::D()//最后构造自己
-------复制构造函数-------
int A::A()
int M::M()
int A::A()
int N::N()
int B::B()
int C::C()
int E::E()
int D::D(D &a)//因为D中定义了复制构造函数,并且没有显式调用父类的构造函数,所以所有的“虚基类”和“直接父类”都调用默认构造函数
-------赋值操作符-------
int D::operator=(D &a) //因为显式调用了赋值操作符,那么就只调用自己的代码,不会隐式调用其它的函数
-------析构函数-------
int D::~D()
int E::~E()
int C::~C()
int B::~B()
int N::~N()
int A::~A()
int M::~M()
int A::~A()//因为main函数中定义了两个D对象,所以main函数结束时要进行析构两个D对象。析构的顺序与 构造函数相反。
int D::~D()
int E::~E()
int C::~C()
int B::~B()
int N::~N()
int A::~A()
int M::~M()
int A::~A()

Press any key to continue.

继承构造函数的执行顺序,布布扣,bubuko.com

时间: 2024-12-29 12:00:50

继承构造函数的执行顺序的相关文章

Java的初始化块、静态初始化块、构造函数的执行顺序及用途探究

随笔- 40  文章- 0  评论- 1 Java的初始化块.静态初始化块.构造函数的执行顺序及用途探究 Java与C++有一个不同之处在于,Java不但有构造函数,还有一个”初始化块“(Initialization Block)的概念.下面探究一下它的执行顺序与可能的用途. 执行顺序 首先定义A, B, C三个类用作测试,其中B继承了A,C又继承了B,并分别给它们加上静态初始化块.非静态初始化块和构造函数,里面都是一句简单的输出. 主类Main里面也如法炮制. 1 class A { 2 st

关于子类对象的构造函数和父类构造函数的执行顺序

我们分别为父类和子类添加显式的构造函数,代码如下: class Person     {         private int nAge;         protected string strName;         double douHeight;         public string strEateType;         //父类的构造函数         public Person()         {             Console.WriteLine("我

C#构造函数的执行顺序

<1> using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace 构造函数的执行顺序 { public class MyBaseClass { public MyBaseClass() { Console.Write("调用父类无参数的构造函数"); } public MyBaseClass(int i) { Console.Write(&q

java中子类继承父类程序执行顺序问题

Java中,new一个类的对象,类里面的静态代码块.非静态代码.无参构造方法.有参构造方法.类的一般方法等部分,它们的执行顺序相对来说比较简单,用程序也很容易验证.比如新建一个测试父类. public class FatherTest { private String name; FatherTest(){ System.out.println("--父类的无参构造函数--"); } FatherTest(String name){ this.name=name; System.out

java变量,初始化快,构造函数的执行顺序

转自 http://blog.csdn.net/macheng365/article/details/6403050 —————————————————————————————————————————————————— 对于JAVA中类的初始化是一个很基础的问题,其中的一些问题也是易被学习者所忽略.当在编写代码的时候碰到时,常被这些问题引发的错误,感觉莫名其妙.而且现在许多大公司的面试题,对于这方面的考查也是屡试不爽.不管基于什么原因,我认为,对于java类中的初始化问题,有必要深入的了解.Ja

父类,子类,静态属性,静态代码块,构造代码块,构造函数,执行顺序

1 package demo; 2 //父类 3 public class FatherClass { 4 5 private static String strFather="父类静态属性----1"; 6 7 static{ 8 System.out.println("父类静态代码块----1"); 9 } 10 11 { 12 System.out.println("父类构造代码块----3"); 13 } 14 15 public Fat

Java学习之继承中的执行顺序详解

代码块(理解) (1)用{}括起来的代码. (2)分类: A:局部代码块 用于限定变量的生命周期,及早释放,提高内存利用率. B:构造代码块 把多个构造方法中相同的代码可以放到这里,每个构造方法执行前,首先执行构造代码块. C:静态代码块 static{}对类的数据进行初始化,仅仅只执行一次. (3)静态代码块,构造代码块,构造方法的顺序问题? 静态代码块 > 构造代码块 > 构造方法 class Student { static { System.out.println("Stud

JavaSE8基础 类中代码块与构造函数的执行顺序 静态代码块(only) -&gt; 构造代码块 -&gt; 构造方法

os :windows7 x64    jdk:jdk-8u131-windows-x64    ide:Eclipse Oxygen Release (4.7.0) 代码: /* 静态代码块(only) -> 构造代码块 -> 构造方法 */ class Test { static{ //静态代码块中 System.out.println("静态代码块的代码执行,只执行一次"); } { System.out.println("构造代码块中的代码执行"

静态代码块,普通代码块,构造函数的执行顺序

class Father{ public Father(){ System.out.println("...父类的构造方法..."); } static{ System.out.println("...父类的静态代码块..."); } { System.out.println("...父类的普通代码块..."); } } class Son extends Father{ public Son(){ System.out.println(&quo