| 网站首页 | 业界新闻 | 小组 | 威客 | 人才 | 下载频道 | 博客 | 代码贴 | 在线编程 | 编程论坛
欢迎加入我们,一同切磋技术
用户名:   
 
密 码:  
共有 2426 人关注过本帖
标题:[讨论]关于析构函数的调用顺序
取消只看楼主 加入收藏
幽园香客
Rank: 3Rank: 3
等 级:论坛游侠
帖 子:231
专家分:142
注 册:2006-2-27
结帖率:50%
收藏
 问题点数:0 回复次数:6 
[讨论]关于析构函数的调用顺序

如题,在调用析构函数时,其顺序和构造函数的顺序完全相反。例如:
class A
{
public:
A(){cout<<"A construction"<<endl;}
~A(){cout<<"A destruction"<<endl;}
};
class B
{
public:
B(){cout<<"B construction"<<endl;}
~B(){cout<<"B destruction"<<endl;}
A a;
};

main()
{
B b;
}
则其结果如下:A construction
B construction
B destruction
A destruction
结果验证了上述结论,可是问题就在后两个。
“析构函数只是在类对象生命结束时,由系统调用”---钱能 《C++程序设计教程》
我就搞不清楚了,为什么B对象结束比A对象还早?明明是在B对象中调用A的对象,B先被析构?一旦B被析构,岂不是B对象的一些资源都被释放掉了(假如有的话)?还有如果从调用机理来说,也是说不通的。哪位兄弟知道,到底为什么?谢谢了

[此贴子已经被作者于2007-3-19 16:27:10编辑过]

搜索更多相关主题的帖子: 函数 顺序 
2007-03-19 16:26
幽园香客
Rank: 3Rank: 3
等 级:论坛游侠
帖 子:231
专家分:142
注 册:2006-2-27
收藏
得分:0 

问题关键是:A对象是B类中成员,如果把B对象析构了,那么B对象中所拥有的一切资源都将失去。那么A对象怎么能还调用?


做个有用的人!
2007-03-19 18:56
幽园香客
Rank: 3Rank: 3
等 级:论坛游侠
帖 子:231
专家分:142
注 册:2006-2-27
收藏
得分:0 
楼上说的很形象,也很贴切。我翻阅了几本C++方面的书,都是只是提到析构函数的调用顺序,却总是没有讲为什么是这样。知其然,知其所以然!呵呵,或许,过于钻牛角尖了!不过,总还是希望能够得到一个合理的解释。

[此贴子已经被作者于2007-3-19 21:14:15编辑过]



做个有用的人!
2007-03-19 21:12
幽园香客
Rank: 3Rank: 3
等 级:论坛游侠
帖 子:231
专家分:142
注 册:2006-2-27
收藏
得分:0 
楼上的,其实如果按照上面你说的情况,我想结果更应该是先调用A对象的析构函数,再调用B的析构函数。因为,如果B中不止一个资源需要释放,当释放A对象所占资源时去调用A的析构函数;然后再调用B的析构了。按照我们通常考虑函数嵌套调用的方法去考虑这个问题时,就会得到和事实相反的结果。

做个有用的人!
2007-03-19 22:07
幽园香客
Rank: 3Rank: 3
等 级:论坛游侠
帖 子:231
专家分:142
注 册:2006-2-27
收藏
得分:0 
谢谢6楼和song4!经过这两天的讨论,我对析构函数又有了更进一步认识。

做个有用的人!
2007-03-20 20:28
幽园香客
Rank: 3Rank: 3
等 级:论坛游侠
帖 子:231
专家分:142
注 册:2006-2-27
收藏
得分:0 
这两天,又仔细琢磨了下。觉得问题关键应该是和栈有关。一个最简单的例子:
class CA
{ public:
CA(){cout<<"CA construction"<<endl;}
~CA(){cout<<"CA destruction"<<endl;}
};
class CB
{ public:
CB(){cout<<"CB construction"<<endl;}
~CB(){cout<<"CB destruction"<<endl;}
};
void main()
{
CA a;
CB b;
}
结果还是:CA construction
CB construction
CB destrutcion
CA destruction
在这里没有包含或者被包含的关系,或者是继承与被继承的关系,可是输出结果仍旧是先前我们说的那样。可见,析构函数的处理过程和栈有关系--先进后出。至于在一个类中声明另外类的对象,或者一个类继承另外一个类,都只不过是析构函数的一个特殊应用而已。我想最终还是需要从析构函数的实现原理上去考虑这个问题。呵呵


做个有用的人!
2007-03-24 22:27
幽园香客
Rank: 3Rank: 3
等 级:论坛游侠
帖 子:231
专家分:142
注 册:2006-2-27
收藏
得分:0 
晕,刚才写的那么多东西,提交时出现错误,文字全没了!
谢谢楼上的几位,经过几天来的讨论,我想是不是这样认识这个问题:首先,需要澄清一个错误的认识:调用了子类的析构函数,就释放了占用的所用资源。根据“类与类之间,你做你的,我做我的,以接口作沟通。即使基类与子类也不例外”(引自:钱能 《C++程序设计教程》)的原则,子类的析构函数只是释放自己做申请的那部分资源;基类的资源的释放还是需要调用基类的析构函数。这样以来,基类和子类的的析构函数是各司其职。
总体来说:构造函数是一个入栈过程,而析构函数则是一个出栈的过程。

做个有用的人!
2007-03-25 11:28
快速回复:[讨论]关于析构函数的调用顺序
数据加载中...
 
   



关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.037578 second(s), 8 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved