当前位置: 首页 > wzjs >正文

阿里云申请域名后网站网站建设类岗位杭州

阿里云申请域名后网站,网站建设类岗位杭州,百度网站推广电话,微信里的小程序占内存吗C的虚析构函数 1.语法规则:2.用途:3.原理:示例代码: 4. 下面解释为什么基类未定义为析构函数时,析构子类(派生类)对象也能把基类对象析构的原因4.1核心原理:编译器自动生成的析构函数调用链4.1.1 对象构造与…

C++的虚析构函数

  • 1.语法规则:
  • 2.用途:
  • 3.原理:
        • 示例代码:
  • 4. 下面解释为什么基类未定义为析构函数时,析构子类(派生类)对象也能把基类对象析构的原因
    • 4.1核心原理:编译器自动生成的析构函数调用链
      • 4.1.1 对象构造与析构的镜像对称原则
      • 4.1.2 编译器在派生类析构函数中插入隐式代码
    • 4.2 底层机制分步解析
    • 4.3 技术细节说明
      • 4.3.1.this指针调整
      • 4.3.2.继承链处理
      • 4.3.3.与虚函数无关

1.语法规则:

virtual ~析构函数   // 写了虚析构就不能同时再去写普通析构
{}

父类的指针指向子类对象的时候,如果delete释放父类的指针,那么正常情况下只会调用父类的析构函数,不会调用子类的析构函数(释放不彻底)

2.用途:

把父类的析构函数定义成虚析构就能解决
在继承的时候建议把父类的析构函数定义成虚析构

3.原理:

  • 不加virtual,此时采用静态联编(只调用赋值运算左边的类(父类)析构函数)
Cat c1;
Animal *p=c1; // 父类指针指向子类对象
delete p;
  • 加virtual,此时采用动态联编(依据赋值运算右边的类型(子类),先调用子类析构,再调用父类析构)
Cat c1;
Animal *p=c1; // 父类指针指向子类对象
delete p;
示例代码:
#include <iostream>
using namespace std;/*虚析构为了解决特定的问题,发明的一种语法规则。特定的问题:父类的指针指向子类的堆空间,delete父类指针,默认情况下只会调用父类的析构,不会调用子类的析构解决方法:把父类的析构函数定义成虚析构
*/
class Animal
{
public:Animal(){cout<<"父类动物构造"<<endl;}virtual ~Animal(){cout<<"父类动物析构"<<endl;}
};class Cat:public Animal
{
public:Cat(){cout<<"子类猫构造"<<endl;}~Cat(){cout<<"子类猫析构"<<endl;}
};// void showAnimalEat(Animal *other)
// {// other->eat();// delete other;
// }// Cat *c1=new Cat;
// Dog *d1=new Dog;
// showAnimalEat(c1);
// showAnimalEat(d1);int main()
{Cat *c1=new Cat;//父类的指针指向子类对象Animal *p=c1;//释放堆空间// delete c1; delete p;  //加了virtual,析构就正常了,不加virtual析构不彻底/*不加virtual只会调用基类的析构函数而不调用子类的析构函数:父类动物构造子类猫构造父类动物析构*/
}/*
执行结果: 在基类中加了virtual后不管是delete子类指针还是delete父类指针,都会调用子类的析构函数父类动物构造子类猫构造子类猫析构父类动物析构
*/

4. 下面解释为什么基类未定义为析构函数时,析构子类(派生类)对象也能把基类对象析构的原因

\quad 在C++中,当直接通过派生类指针删除对象时,派生类析构函数能够自动调用基类析构函数的原理,主要基于C++语言标准规定的对象销毁顺序编译器生成的隐式代码机制。以下是详细解释:

4.1核心原理:编译器自动生成的析构函数调用链

4.1.1 对象构造与析构的镜像对称原则

  • 构造顺序:基类构造 → 成员构造 → 派生类构造
  • 析构顺序:派生类析构 → 成员析构 → 基类析构(完全相反)

4.1.2 编译器在派生类析构函数中插入隐式代码

\quad 当编译器处理派生类析构函数时,会自动在函数体末尾添加调用基类析构函数的代码。例如:

// 用户编写的派生类析构函数
~Derived() {// 用户定义的清理代码
}// 编译器实际生成的代码
~Derived() {// 1. 用户定义的清理代码// 2. 析构所有成员对象(按声明逆序)// 3. 调用直接基类的析构函数  <-- 关键!
}

4.2 底层机制分步解析

假设有以下类结构:

class Base {
public:~Base() { /* 基类析构 */ }
};class Derived : public Base {Member m;  // 成员对象
public:~Derived() { /* 派生类析构 */ }
};

当执行 delete d(Derived* d)时:

  1. 调用派生类析构函数

在这里插入图片描述
2) 执行用户代码

// 执行用户编写的析构代码

3) 析构成员对象(编译器插入)

// 编译器自动添加成员析构
m.~Member();  // 逆序析构所有成员

4)调用基类析构函数(编译器插入)

// 编译器自动添加基类析构调用
Base::~Base(this);  // 关键步骤!

5)释放内存

operator delete(d);  // 释放整个对象内存

4.3 技术细节说明

4.3.1.this指针调整

  • 当调用基类析构函数时,编译器会自动将this指针调整到基类子对象的起始位置
  • 例如:Base::~Base(this + offset) → 实际是 Base::~Base( (Base*)this )

4.3.2.继承链处理

对于多级继承:

class GrandBase { /*...*/ };
class Base : public GrandBase { /*...*/ };
class Derived : public Base { /*...*/ };

编译器生成的 ~Derived() 会:

~Derived() {// 用户代码// 析构成员Base::~Base(this);    // 调用直接基类// 实际在~Base()中会再调用GrandBase::~GrandBase()
}

4.3.3.与虚函数无关

此过程完全在编译时确定:

  • 不依赖虚函数表(vtable)
  • 不涉及运行时动态查找
  • 是静态绑定的函数调用
http://www.dtcms.com/wzjs/561637.html

相关文章:

  • 做书的网站有哪些中小企业解决方案
  • 做网站哪里最好网页编辑软件中文版
  • 下载 公司网站 程序 需要ftp权限天津关键词排名提升
  • 如何做网站拓扑结构图自己做交易网站吗
  • 关键词搜索引擎工具爱站wordpress会员注册
  • 达濠市政建设有限公司网站厦门网络营销顾问
  • 重庆梁平网站建设公司免费发布信息的平台
  • 中山专业门户网站制作策划外贸wordpress模板
  • 经典网站设计欣赏微信小程序云开发模板
  • 做服装外贸哪个网站好东莞网站建设服务有什
  • 佛山微网站开发哪家好网上购物系统概述
  • 制造业网站开发浙江核酸检测查验
  • 个人电脑做网站主机通过wordpress小程序发布文章
  • 怎样辨别网站提供建站服务的网络公司的比较
  • 做英语作业的网站中企动力邮箱设置
  • 湘潭市高新建设局网站天津中冀建设集团有限公司网站
  • iis网站正在建设中学做网站有前
  • 企业网站的开发流程是什么最新seo快排技术qq
  • 手机型号最全的网站文创产品设计创意图片
  • 导购网站怎么推广无人区卡一卡二卡三乱码入口
  • 哪里有免费做网站子公司怎么注册
  • 西安做公司网站网站开发阶段流程
  • 优秀网站网页设计分析百度指数平台
  • 天津网站建设公司如何设置自己的网站
  • 清溪做网站的电话c2c模式举例子
  • 济南网站建设0531soso深圳专业的网站建设
  • 网站建设最低多少钱上海专业网站建设 公司
  • 网站建设的途径ssl aws wordpress
  • 外贸网站建设怎么制作数据查询插件 wordpress
  • 盐山网站开发潍坊专业网站制作公司营销