博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
【C++】构造函数 析构函数 调用顺序
阅读量:3926 次
发布时间:2019-05-23

本文共 2739 字,大约阅读时间需要 9 分钟。

微信搜索:编程笔记本。获取更多干货!

微信搜索:编程笔记本。获取更多干货!

点击上方蓝字关注我,我们一起学编程

欢迎小伙伴们分享、转载、私信、赞赏

今天我们来探讨一下类继承中的构造函数和析构函数的调用顺序问题。

#include 
using namespace std;class Father {
public: Father() {
cout << "Father constructor worked\n" << endl; } ~Father() {
cout << "Father destructor worked\n" << endl; }};class Son : public Father {
public: Son() {
cout << "Son constructor worked\n" << endl; } ~Son() {
cout << "Son destructor worked\n" << endl; }};int main(){
Son son; return 0;}

微信搜索:编程笔记本。获取更多干货!

微信搜索:编程笔记本。获取更多干货!

上面的代码中,Son 公有继承 Father ,当我们定义一个 Son 的对象时,基类和派生类的构造函数与析构函数调用顺粗如下:

Father constructor workedSon constructor workedSon destructor workedFather destructor worked

可以看到,构造函数是从基类向派生类逐层调用的,析构函数是从派生类向基类逐层调用的。

问了更好地说明问题,我们增加一个类:

#include 
using namespace std;class GrandFather {
public: GrandFather() {
cout << "GrandFather constructor worked\n" << endl; } ~GrandFather() {
cout << "GrandFather destructor worked\n" << endl; }};class Father : public GrandFather {
public: Father() {
cout << "Father constructor worked\n" << endl; } ~Father() {
cout << "Father destructor worked\n" << endl; }};class Son : public Father {
public: Son() {
cout << "Son constructor worked\n" << endl; } ~Son() {
cout << "Son destructor worked\n" << endl; }};int main(){
Son son; return 0;}/*运行结果:GrandFather constructor workedFather constructor workedSon constructor workedSon destructor workedFather destructor workedGrandFather destructor worked*/

微信搜索:编程笔记本。获取更多干货!

微信搜索:编程笔记本。获取更多干货!

构造函数调用顺序:从长辈到小辈;析构函数调用顺序:从小辈到长辈。

同样地,生成对象数组与生成单个对象的情况相同,不再赘述,附上测试代码。

#include 
using namespace std;class GrandFather {
public: GrandFather() {
cout << "GrandFather constructor worked\n" << endl; } ~GrandFather() {
cout << "GrandFather destructor worked\n" << endl; }};class Father : public GrandFather {
public: Father() {
cout << "Father constructor worked\n" << endl; } ~Father() {
cout << "Father destructor worked\n" << endl; }};class Son : public Father {
public: Son() {
cout << "Son constructor worked\n" << endl; } ~Son() {
cout << "Son destructor worked\n" << endl; }};int main(){
Son *pSon = new Son[2]; delete[] pSon; return 0;}/*运行结果:GrandFather constructor workedFather constructor workedSon constructor workedGrandFather constructor workedFather constructor workedSon constructor workedSon destructor workedFather destructor workedGrandFather destructor workedSon destructor workedFather destructor workedGrandFather destructor worked*/

在上面的例子中,若 delete pSon 的话,会报 munmap_chunk(): invalid pointer, Aborted (core dumped) 错误。

总结

对于具有继承关系的类,其构造函数的调用顺序是:先基类、再派生类;其析构函数的调用顺序是:先派生、后基类。

微信搜索:编程笔记本。获取更多干货!

微信搜索:编程笔记本。获取更多干货!

你可能感兴趣的文章
为什么曾经优秀的人突然变得平庸?
查看>>
.NET 5 中的隐藏特性
查看>>
.NET5都来了,你还不知道怎么部署到linux?最全部署方案,总有一款适合你
查看>>
我画着图,FluentAPI 她自己就生成了
查看>>
BenchmarkDotNet v0.12x新增功能
查看>>
使用 .NET 5 体验大数据和机器学习
查看>>
C# 中的数字分隔符 _
查看>>
使用 docker 构建分布式调用链跟踪框架skywalking
查看>>
Github Actions 中 Service Container 的使用
查看>>
别在.NET死忠粉面前黑.NET5,它未来可期!
查看>>
Winform 进度条弹窗和任务控制
查看>>
部署Dotnet Core应用到Kubernetes(二)
查看>>
持续交付二:为什么需要多个环境
查看>>
FreeSql接入CAP的实践
查看>>
浅析 EF Core 5 中的 DbContextFactory
查看>>
听说容器正在吃掉整个软件世界?
查看>>
真实经历:整整一年了,他是这样从程序员转型做产品经理的
查看>>
netcore一键部署到linux服务器以服务方式后台运行
查看>>
还在犹豫是否迁移.NET5?这几个项目已经上线了!
查看>>
被 C# 的 ThreadStatic 标记的静态变量,都存放在哪里了?
查看>>