转至繁体中文版     | 网站首页 | 图文教程 | 资源下载 | 站长博客 | 图片素材 | 武汉seo | 武汉网站优化 | 
最新公告:     敏韬网|教学资源学习资料永久免费分享站!  [mintao  2008年9月2日]        
您现在的位置: 学习笔记 >> 图文教程 >> 软件开发 >> Delphi程序 >> 正文
我的文章-《剖析Delphi中的构造和析构》         ★★★★

我的文章-《剖析Delphi中的构造和析构》

作者:闵涛 文章来源:闵涛的学习笔记 点击数:1372 更新时间:2009/4/23 18:30:22
;内存泄露”。所以为了保证正确地析构对象,析构函数都需要加override声明。
3.2 对象销毁的全过程
先销毁派生类子对象,再销毁基类子对象。
 提  示
在派生类中,基类子对象指从基类中继承的部分,派生类中子对象是指新增的部分。
3.3 destroy, free, freeAndNil, release用法和区别
destroy:虚方法
 释放内存,在Tobject中声明为virtual,通常是在其子类中override 它,且要加上inherited关键字,才能保证派生类对象正确地被销毁;
但destroy一般不能直接用,为什么?
假如当一个对象为nil,我们仍然调用destroy,此时会产生错误。因为destroy是虚方法,它要根据对象中的头四个字节找到虚拟方法表Vmt的入口地址,从而找到destroy的入口地址,所以此时对象一定要存在。但free就是静态方法,它只需根据对象引用/指针的类型来确定,即使对象本身不存在也没问题,而且在free中有判断对象是否存在的操作, 所以用free比用destroy安全。
2)free:静态方法
测试对象是否为nil, 非nil则调用destroy。下面是free的Delphi代码:
procedure Tobject.Free;
 begin
   if Self <> nil then
     Destroy;
  end;
 一静一动,取长补短,岂不妙哉!
不过,调用Destroy只是把对象销毁了,但并没有把对象的引用设为nil,这需要程序员来完成,不过自从Delphi5之后,在sysUtils单元中提供了一个freeAndNil。
 3)freeAndNil;一般方法,非对象方法,非类方法。
SysUtils单元中FreeAndNil 定义
procedure FreeAndNil(var Obj);
var
  Temp: TObject;
begin
  Temp := TObject(Obj);
  Pointer(Obj) := nil;
  Temp.Free;
end;
建议大家用它代替free/Destroy,以便确保正确地释放对象。
4)release;TcustomForm中定义的静态方法。
当窗口中所有的事件处理完之后,才调用free函数。常用在销毁窗口,而在这个窗口中事件处理需要一定的时间的时候,用这个方法能确保窗口事件处理完之后才销毁窗口。下面是TCustomForm.Release的Delphi源代码:
procedure TCustomForm.Release;
begin
  PostMessage(Handle, CM_RELEASE, 0, 0);
//向窗口发CM_RELEASE消息到消息队列,当所有的窗口事件消息处理完之后,
//再调用CM_RELEASE消息处理过程CMRelease
end;
再看看下面CM_RELEASE消息处理过程CMRelease的定义:
procedure CMRelease(var Message: TMessage); message CM_RELEASE;
procedure TCustomForm.CMRelease;
begin
Free; //最后还是free;
end;
4 VCL构造&析构体系结构
 
TObject   
constructor Create;//静态方法
destructor Destroy; virtual; 

 


 
TPersistent   
destructor Destroy; override; 

 


TComponent   
constructor Create(AOwner: TComponent); virtual;
destructor Destroy; override; 

 


 
TControl   
constructor Create(AOwner: TComponent); override;
destructor Destroy; override; 

 


                                       …
下面分析VCL中的构造和析构的源代码,以Tcontrol为例:
constructor TControl.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);//创建基类子对象,并把析构权移交给AOwner。放在最前面
   //这样就保证了“先创建基类子对象,再创建派生类子对象”的顺序
  …//初始化,以及调用内部子对象的构造函数
end;

destructor TControl.Destroy;
begin
  …//析构派生类中内部子对象
  inherited Destroy;//析构基类对象,放在最后面
  //这样就保证了“先析构派生类子对象,再析构基类子对象”的顺序
end;
5 正确使用构造函数和析构函数
   经过上面的分析,下面总结一下使用构造函数和析构函数的原则:
在使用对象之前,必须先建立一个对象时,并且及时销毁对象,以释放资源。
两个对象引用赋值时,要确保出现的无名对象(指没有被引用的对象)能被释放。
当创建一个组件时,建议设置一个宿主组件(即使用AOwner参数,通常是窗体),由Aowner来管理对象的销毁,那么就不必惦记着销毁该组件了,这是Delphi在窗体上/数据模块设计并创建组件是采用的方法。所以我们不必书写调用该组件的析构函数。
当函数的返回类型为对象时,那么Result也是对象的引用,确保Result引用的对象要存在。
若要使用obj<>nil 或assigned(nil)测试对象存在时,在调用析构之后还应obj:=nil。

请参考演示程序的源代码
说明(建议要有)
所有的Delphi程序已在win2k+Delphi6 sp2 上通过,对于C++程序,只是为了说明与Delphi中不同,并不保证能直接运行。为了加深对本篇文章的理解,建议参考演示程序。
这篇文章包括了我在学习VCL/RTL中的一些经验和体会,加上本人的个人能力有限,难免出现错误,请大家不吝指正!
在阅读本篇文章之前,需要读者对Oriented Pascal语言有一定的了解,并能理解多态,如果您对其中一些概念还不是很清楚的话,请参考相关文章。
通过本篇文章,你应该能比较清楚地理解Delphi中的对象模型、构造&析构实现机制以及VCL中构造&析构 体系结构,并能掌握使用构造&析构的使用方法。Delphi中的构造&析构相当于C++中的算是简单多了,我们应该能掌握它。

上一页  [1] [2] 


[Delphi程序]我的文章-《剖析Delphi中的多态》  
教程录入:mintao    责任编辑:mintao 
  • 上一篇教程:

  • 下一篇教程:
  • 【字体: 】【发表评论】【加入收藏】【告诉好友】【打印此文】【关闭窗口
      注:本站部分文章源于互联网,版权归原作者所有!如有侵权,请原作者与本站联系,本站将立即删除! 本站文章除特别注明外均可转载,但需注明出处! [MinTao学以致用网]
      网友评论:(只显示最新10条。评论内容只代表网友观点,与本站立场无关!)

    同类栏目
    · C语言系列  · VB.NET程序
    · JAVA开发  · Delphi程序
    · 脚本语言
    更多内容
    热门推荐 更多内容
  • 没有教程
  • 赞助链接
    更多内容
    闵涛博文 更多关于武汉SEO的内容
    500 - 内部服务器错误。

    500 - 内部服务器错误。

    您查找的资源存在问题,因而无法显示。

    | 设为首页 |加入收藏 | 联系站长 | 友情链接 | 版权申明 | 广告服务
    MinTao学以致用网

    Copyright @ 2007-2012 敏韬网(敏而好学,文韬武略--MinTao.Net)(学习笔记) Inc All Rights Reserved.
    闵涛 投放广告、内容合作请Q我! E_mail:admin@mintao.net(欢迎提供学习资源)

    站长:MinTao ICP备案号:鄂ICP备11006601号-18

    闵涛站盟:医药大全-武穴网A打造BCD……
    咸宁网络警察报警平台