zoukankan      html  css  js  c++  java
  • 构造函数和析构函数

    构造函数和析构函数在类中的调用顺序:

    1)构造函数:

    定义一个对象时先调用基类的构造函数、然后调用派生类的构造函数。

    1)析构函数:

    析构与构造的过程恰好相反:先调用派生类的析构函数、然后调用基类的析构函数。

    注意:由于vs2013无法显示输出析构函数的内容,所以采用输出到文本中的方式。

     1 #include<iostream>
     2 #include <fstream>
     3 using namespace std;
     4 
     5 fstream fout("D:\Downloads\destructor.txt", ios::app);
     6 class Base {
     7 public:
     8     Base(int c) { fout << "基类带参构造函数" << c << endl; }
     9     ~Base() { fout << "基类析构" << endl; }
    10 };
    11 class Derived :public Base {
    12 public:
    13     Derived(int c) :Base(c) // 显式调用基类构造函数
    14     {
    15         fout << "派生类带参构造函数" << c << endl;
    16     }
    17     ~Derived() { fout << "派生类析构" << endl; }
    18 };
    19 int main()
    20 {
    21     int i = 9;
    22     Derived d1(i);
    23     system("pause");
    24     return 0;
    25 }

    输出结果:

    基类带参构造函数9
    派生类带参构造函数9
    派生类析构
    基类析构


     1 #include<iostream>
     2 #include <fstream>
     3 using namespace std;
     4 
     5 fstream fout("D:\Downloads\destructor.txt", ios::app);
     6 //创建一个汽车类
     7 class Car
     8 {
     9 public:
    10     //构造函数
    11     Car(short, int);
    12     //析构函数
    13     ~Car();
    14     void move();
    15 private:
    16     short speed;
    17     int num;
    18 };
    19 
    20 Car::Car(short s, int n)
    21 {
    22     speed = s;
    23     num = n;
    24     fout << "创建第" << num << "辆车,速度是" << speed << " 米/秒" << endl;
    25 }
    26 Car::~Car()
    27 {
    28     fout << "销毁掉第 " << num << "辆车" << endl;
    29 }
    30 void Car::move()
    31 {
    32     fout << "" << num << "辆车速度是" << speed << endl;
    33 }
    34 //主函数
    35 void main()
    36 {
    37     //先创建第car1对象,再创建car2对象
    38     Car car1(10, 1), car2(20, 2);
    39     car1.move();
    40     car2.move();
    41 }

    输出结果:

    创建第1辆车,速度是10 米/秒
    创建第2辆车,速度是20 米/秒
    第 1辆车速度是10
    第 2辆车速度是20
    销毁掉第 2辆车
    销毁掉第 1辆车

    解析:

    在主函数中是首先创建了Car类的car1对象,后创建了car2对象,所以在执行构造函数的顺序上,是先执行car1对象的构造函数,后执行car2对象的构造函数。而在主函数执行结束,要调用析构函数的时候,根据开始说的法则,则会先执行car2类的析构函数,后执行car1类的析构函数。这就是“使用构造函数创建对象的顺序与使用析构函数释放对象的顺序相反”这条法则的一个很好的体现。


     1 #include <iostream>
     2 using namespace std;
     3 class A{
     4 public:
     5        A(){cout<<"Construct a"<<endl;p();}
     6        virtual void p(){cout<<"A"<<endl;}
     7        ~A(){cout<<"Destruct a"<<endl;p();}   
     8 };
     9 class B : public A{
    10 public:
    11        B(){cout<<"Construct b"<<endl;p();}
    12        void p(){cout<<"B"<<endl;}
    13        ~B(){cout<<"Destruct b"<<endl;p();}    
    14 };
    15 int main()
    16 {
    17     A *a=new B();
    18     delete a;
    19     getchar();
    20     return 0;
    21 }

    打印的结果是:
    Construct a
    A
    Construct b
    B
    Destruct a
    A

    • 这是一段极易出错的程序,如果用的话 出现的就是先析构 B类 再析构A类 
     B *a=new B();

    打印的结果是:
    Construct a 

    Construct b 

    Destruct b 

    Destruct a 

    A *a = new B;
    虽然指针a指向B类型,但指针a的类型是A。
    delete a时将调用类型A的析构函数;
    因为:如果A的析构函数是虚函数,则:
    delete a时调用类型A的析构函数步骤如下:
    1,到虚函数映射表中查找A的实际析构函数;
    2,发现被实例化为B的析构函数;
    3,调用B的析构函数;
    4,调用A的析构函数---如果A的析构不是纯虚函数的话。

  • 相关阅读:
    Eclipse 软件 Java 解决:出现的editor does not contain a main type错误框 问题
    Oracle SQL高级编程——分析函数(窗口函数)全面讲解
    瑞联科技:Pwp3框架 调用存储过程返还数据集合 到前端界面展示
    spring jdbctemplate调用存储过程,返回list对象
    利用jquery操作Radio方法小结
    Oracle临时表
    JdbcUtil
    整理oracle 树形查询
    Js:消息弹出框、获取时间区间、时间格式、easyui datebox 自定义校验、表单数据转化json、控制两个日期不能只填一个
    Java对象之间的深度复制拷贝
  • 原文地址:https://www.cnblogs.com/Bella2017/p/9512972.html
Copyright © 2011-2022 走看看