直接上例子了,基础知识自己去了解,首先定义一个类:

  TPerson = class
public
name: string;
age: Integer;
constructor Create(name: string; age: Integer);
end; constructor TPerson.Create(name: string; age: Integer);
begin
Self.name := name;
Self.age := age;
end;

例子1,首先了解Free,仅仅是销毁堆中数据,栈中变量的值依然是堆中的地址:

procedure TForm3.btn1Click(Sender: TObject);
var
ps: TPerson;
begin
ps := TPerson.Create('小李', 10); ps.Free; //这里调用Free,堆中的数据已经被释放,但是ps这个指针的值还是堆中对象的地址 if Assigned(ps) then //Assigned方法,当ps指针的值为nil的时候,才返回False,由于ps的值不为nil,这里显然会返回True
begin
mmo1.Lines.Add('yes');
mmo1.Lines.Add(ps.name); //这里产生了Av错误,原因是ps堆中的对象已经被释放
end else begin
mmo1.Lines.Add('no');
end;
end;

例子2,知道即使你不创建实例,Assigned依然是true;

procedure TForm3.btn3Click(Sender: TObject);
var
p: TPerson;
begin
//p不初始化,会自由随机分配一个地址和值,值也是原来的自由值,不一定是nil,通常都不是nil
if Assigned(p) then
begin
//只要p指针的值不是nil,这里就会返回true,所以是yes
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no');
end;
end;

例子3:对例子1进行改造,使用FreeAndNil,将堆中数据释放,同时将栈中指针的值变为nil;

procedure TForm3.btn3Click(Sender: TObject);
var
ps: TPerson;
begin
ps := TPerson.Create('小李', 10); FreeAndNil(ps); //指针的值也变成nil了 if Assigned(ps) then
begin
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no'); //此时就自然到这里了
end;
end;

例子4,最后一个例子,得出官方的Assigned 不是我们需要的:

procedure TForm3.btn4Click(Sender: TObject);
var
ps, ps1: TPerson;
begin
ps := TPerson.Create('小李', 10); ps1 := ps; FreeAndNil(ps); if Assigned(ps) then
begin
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no'); //ps指针的值是nil了,所以no
end; if Assigned(ps1) then
begin
mmo1.Lines.Add('yes'); //ps1指针的值不是nil
//mmo1.Lines.Add(ps1.name); //这里就会报错,因为ps堆中的数据已经释放
end else begin
mmo1.Lines.Add('no');
end; //显然上面不是我们要的结果,使用我们自己的函数
if AssignedEx(ps1, TPerson) then
begin
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no'); //由于ps1指向的堆中数据已经不存在,这里会no
end;
end;

好了综上得出官方的Assigned 有点简陋,不是我们需要的,引出我们的修改版:

/// <summary>
/// 判断实例释放释放
/// </summary>
/// <param name="AVar">实例变量</param>
/// <param name="className">实例类型</param>
function AssignedEx(AVar: TObject; AClass: TClass): Boolean;
begin
//首先判断变量指针的值是否为nil
if not Assigned(AVar) then
begin
Exit(False);
end; //判断堆中的数据是否是当前类
try
//若AVar指向的堆中数据已释放,则这里调用.ClassName会AV异常
if AVar.ClassName = AClass.ClassName then
begin
Exit(True);
end else begin
Exit(False);
end;
except
//有异常说明堆中已经被释放掉了
Exit(False);
end;
end;

==========================================================

最后贴上全部测试代码:

全部测试代码
unit Unit3;

interface

uses
Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics,
Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.StdCtrls; type
TForm3 = class(TForm)
mmo1: TMemo;
btn1: TButton;
btn2: TButton;
btn3: TButton;
btn4: TButton;
btn5: TButton;
procedure btn1Click(Sender: TObject);
procedure btn2Click(Sender: TObject);
procedure btn3Click(Sender: TObject);
procedure btn4Click(Sender: TObject);
procedure btn5Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end; TPerson = class
public
name: string;
age: Integer;
constructor Create(name: string; age: Integer);
end; var
Form3: TForm3; implementation {$R *.dfm} constructor TPerson.Create(name: string; age: Integer);
begin
Self.name := name;
Self.age := age;
end; /// <summary>
/// 判断实例释放释放
/// </summary>
/// <param name="AVar">实例变量</param>
/// <param name="className">实例类型</param>
function AssignedEx(AVar: TObject; AClass: TClass): Boolean;
begin
//首先判断变量指针的值是否为nil
if not Assigned(AVar) then
begin
Exit(False);
end; //判断堆中的数据是否是当前类
try
//若AVar指向的堆中数据已释放,则这里调用.ClassName会AV异常
if AVar.ClassName = AClass.ClassName then
begin
Exit(True);
end else begin
Exit(False);
end;
except
//有异常说明堆中已经被释放掉了
Exit(False);
end;
end; procedure TForm3.btn1Click(Sender: TObject);
var
ps: TPerson;
begin
ps := TPerson.Create('小李', 10); ps.Free; //这里调用Free,堆中的数据已经被释放,但是ps这个指针的值还是堆中对象的地址 if Assigned(ps) then //Assigned方法,当ps指针的值为nil的时候,才返回False,由于ps的值不为nil,这里显然会返回True
begin
mmo1.Lines.Add('yes');
mmo1.Lines.Add(ps.name); //这里产生了Av错误,原因是ps堆中的对象已经被释放
end else begin
mmo1.Lines.Add('no');
end;
end; procedure TForm3.btn2Click(Sender: TObject);
var
p: TPerson;
begin
//p不初始化,会自由随机分配一个指针,指针的值也是原来的自由值,不一定是nil
if Assigned(p) then
begin
//只要p指针的值不是nil,这里就会返回true,所以是yes
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no');
end;
end; procedure TForm3.btn3Click(Sender: TObject);
var
ps: TPerson;
begin
ps := TPerson.Create('小李', 10); FreeAndNil(ps); //指针的值也变成nil了 if Assigned(ps) then
begin
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no'); //此时就自然到这里了
end;
end; procedure TForm3.btn4Click(Sender: TObject);
var
ps, ps1: TPerson;
begin
ps := TPerson.Create('小李', 10); ps1 := ps; FreeAndNil(ps); if Assigned(ps) then
begin
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no'); //ps指针的值是nil了,所以no
end; if Assigned(ps1) then
begin
mmo1.Lines.Add('yes'); //ps1指针的值不是nil
//mmo1.Lines.Add(ps1.name); //这里就会报错,因为ps堆中的数据已经释放
end else begin
mmo1.Lines.Add('no');
end; //显然上面不是我们要的结果,使用我们自己的函数
if AssignedEx(ps1, TPerson) then
begin
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no'); //由于ps1指向的堆中数据已经不存在,这里会no
end;
end; procedure TForm3.btn5Click(Sender: TObject);
var
ps, ps1: TPerson;
begin
ps := TPerson.Create('小李', 10); ps1 := ps; FreeAndNil(ps); if Assigned(ps) then
begin
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no'); //ps指针的值是nil了,所以no
end; if Assigned(ps1) then
begin
mmo1.Lines.Add('yes'); //ps1指针的值不是nil
//mmo1.Lines.Add(ps1.name); //这里就会报错,因为ps堆中的数据已经释放
end else begin
mmo1.Lines.Add('no');
end; //显然上面不是我们要的结果,使用我们自己的函数
if AssignedEx(ps1, TPerson) then
begin
mmo1.Lines.Add('yes');
end else begin
mmo1.Lines.Add('no'); //由于ps1指向的堆中数据已经不存在,这里会no
end;
end; end.

Delphi-判断一个对象是否释放,改造官方的Assigned的更多相关文章

  1. Delphi中关于资源释放(Free,Relealse,FreeAndNil)

    根据日常编程经验,得出一些Delphi中关于资源释放的体会. 假如有对象Obj为TObject类型: 1) Obj.Free直接释放资源后,调用OnDestroy事件,但是没有将Obj指针值置为Nil ...

  2. win10 uwp 如何判断一个对象被移除

    原文:win10 uwp 如何判断一个对象被移除 有时候需要知道某个元素是否已经被移除,在优化内存的时候,有时候无法判断一个元素是否在某个地方被引用,就需要判断对象设置空时是否被回收. 本文告诉大家一 ...

  3. 2018-8-10-win10-uwp-如何判断一个对象被移除

    title author date CreateTime categories win10 uwp 如何判断一个对象被移除 lindexi 2018-08-10 19:16:50 +0800 2018 ...

  4. java面试一日一题:如何判断一个对象是否为垃圾对象

    问题:请讲下在java中如何判断一个对象是否为垃圾 分析:该问题主要考察对java中的垃圾回收,用什么方式去识别一个对象是垃圾: 回答要点: 主要从以下几点去考虑, 1.GC回收的是什么,回收发生在内 ...

  5. JS心得——判断一个对象是否为空

    判断一个对象是否为空对象,本文给出三种判断方法: 最常见的思路,for...in...遍历属性,为真则为"非空数组":否则为"空数组" 2.通过JSON自带的. ...

  6. Delphi的分配及释放---New/Dispose, GetMem/FreeMem及其它函数的区别与相同

    转载自:http://www.cnblogs.com/qiusl/p/4028437.html?utm_source=tuicool 我估摸着内存分配+释放是个基础的函数,有些人可能没注意此类函数或细 ...

  7. delphi.memory.分配及释放---New/Dispose, GetMem/FreeMem及其它函数的区别与相同

    我估摸着内存分配+释放是个基础函数,有些人可能没注意此类函数或细究,但我觉得还是弄明白的好. 介绍下面内存函数前,先说一下MM的一些过程,如不关心可忽略: TMemoryManager = recor ...

  8. javascript-如何判断一个对象为数组

    Q:如何判断一个对象是否为数组? A1:判断对象的constructor是否指向Array, 接着判断对应的特殊属性,如length,splice之类.这个很容易冒充. A2:使用instanceof ...

  9. delphi 判断是否出现滚动条

    delphi 判断是否出现滚动条     if (GetWindowlong(Stringgrid1.Handle, GWL_STYLE) and WS_VSCROLL) <> 0 the ...

  10. 使用js判断一个对象是否为空 比如 obj={}

    今天使用到js判断一个对象是否为空,js没有封装好的方法,这里最好的办法就是使用jquery里面的封装好的方法 $.isEmptyObject(obj)

随机推荐

  1. vue 状态管理 一、状态管理概念和基本结构

    系列导航 vue 状态管理 一.状态管理概念和基本结构 vue 状态管理 二.状态管理的基本使用 vue 状态管理 三.Mutations和Getters用法 vue 状态管理 四.Action用法 ...

  2. MES系统初探(一)

    什么是MES系统 MES系统是制造执行系统(Manufacturing Execution System)的缩写,是一种用于监控.控制和优化制造过程的软件系统.它主要负责协调生产计划.生产调度.生产执 ...

  3. plsql打开报错:Control 'dxDockBrowserPanel' has no parent window问题解决

    一.现象: 使用plsql登陆oracle数据库时,登陆信息没有报错,但是最后一步报错,重启电脑依然没有解决 一直报:" Control 'dxDockBrowserPanel' has n ...

  4. java基础(3)--pulic class与class的区别

    1.一个类前面的public是可有可无的2.如果一个类使用 public 修饰,则文件名必须与类名一致3.如果一个类前面没有使用public修饰,则文件名可以与类名不一致.当编译成功后会生成对应类名的 ...

  5. 基于java+springboot的家教预约网站、家教信息管理系统

    该系统是基于java+springboot开发的家教预约网站.是给师妹开发的实习作品.学习过程中,遇到问题可以在github咨询作者. 演示地址 前台地址: http://jiajiao.gitapp ...

  6. [转帖]2024年正常使用windows XP之一:系统下载篇

    https://zhuanlan.zhihu.com/p/347764175 半夏:2024年正常使用windows XP之一:系统下载篇 半夏:2024年正常使用windows XP之二:补丁及运行 ...

  7. [转帖]TNS-12535 TNS-00505的处理方法

    硬件说明: 操作系统版本:ORACLE LINUX 6.3  64位 数据库版本:11.2.0.3   64位 问题说明: 在检查数据库的alert日志的时候,发现大量的12170和TNS-12535 ...

  8. [转帖]讨论在 Linux Control Groups 中运行 Java 应用程序的暂停问题原创

    https://heapdump.cn/article/1930426 说明 本篇原文来自 LinkedIn 的 Zhenyun Zhuang,原文:Application Pauses When R ...

  9. vue数据不响应,可能是用法有问题

    <template> <div> <div> <span>用户名: {{ userInfo.name }}</span> <span& ...

  10. 【JS 逆向百例】有道翻译接口参数逆向

    逆向目标 目标:有道翻译接口参数 主页:https://fanyi.youdao.com/ 接口:https://fanyi.youdao.com/translate_o?smartresult=di ...