首先看下面的示例代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
type TTestInterface=class(TInterfacedObject) public destructor Destroy;override; end; procedure TForm1.BitBtn1Click(Sender: TObject); var ATest:IInterface; begin ATest:=TTestInterface.Create; TThread.ForceQueue(nil,procedure begin ShowMessage(IntToStr(ATest._AddRef)); ATest._Release; end); end; { TTestInterface } destructor TTestInterface.Destroy; begin ShowMessage('Object Free'); inherited; end; |
一般来说,我们认为 Delphi 自己管理接口的引用计数,所以不太会注意,但是,在上面的示例中,由于要保证 ATest 在匿名函数中的可用性,Delphi 并没有在函数退出时,减少 ATest 的引用计数,而在匿名函数执行完成后,同样也并没有减少计数,这就造成了 ATest 实例的引用计数没有减少到0,然后就出现了内存泄露的问题。这块已知在10.3.1中已经不存在该问题,感谢菜根提醒。
至于当前的策略,在你的匿名函数调用退出前,将 ATest 的地址设置为 nil 就可以了。