如果我在销毁对象后使用它,为什么我没有收到异常?

Why I don't receive Exception if I use the object after I destroy it?

以下代码工作正常,但不应该!当我单击 Button1 时,该对象首先被销毁,然后使用它的值,我没有收到任何访问冲突或其他东西......更重要的是,乘法运算给出了正确的结果,这证明 Obj1 没有被摧毁!但话又说回来,这也不是真的,因为当我关闭程序时,它不会报告任何内存泄漏。我很困惑。

unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls;

type
  MyObj = class(TObject)
   Value: Cardinal;
  end;

  TForm1 = class(TForm)
    Button1: TButton;
    procedure FormCreate(Sender: TObject);
    procedure Button1Click(Sender: TObject);
  public
   Obj1:MyObj;
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
begin
 Obj1.Free;
 Obj1.Value:=Obj1.Value * 5;
 Caption:=IntToStr(Obj1.Value);
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
 ReportMemoryLeaksOnShutdown:=true;
 Obj1:=MyObj.Create;
 Obj1.Value:=10;
end;

end.

对象被销毁。内存返回给内存管理器。接下来发生的事情是你无法控制的。内存可以返回给系统。在这种情况下,您会看到运行时错误。或者,内存管理器可以使内存保持活动状态,以便在下次程序请求该大小的块时重新使用。这就是这里发生的事情。

您的程序表现出未定义的行为。任何事情都可能发生,包括程序似乎有效。显然这个程序是错误的,你不能在对象被销毁后访问它们。

如果您使用 FastMM 的完整调试版本,那么您应该会看到一个错误,因为在这种情况下,会采取步骤来检测释放后的访问。这是一个有用的调试工具。