Delphi: 为什么会产生内存泄漏?
Delphi: Why does this generate a memory leak?
为什么 TDemo.TBuilder 没有自动释放并产生内存泄漏?
TDemo.TBuilder 应该自动释放,因为这是一个基于 IInterface
的 TInterfacedObject 对象
type
TDemo = class
public type
TBuilder = class(TInterfacedObject)
public
function Generate: TDemo;
end;
public
class procedure Using;
end;
implementation
function TDemo.TBuilder.Generate: TDemo;
begin
Result := TDemo.Create;
// on finish this method, TDemo.TBuilder should be freed !
end;
class procedure TDemo.Using;
begin
with TDemo.TBuilder.Create.Generate do try
// use TDemo
finally
Free;
end;
end;
您有内存泄漏,因为 TBuilder.Create
returns 对象引用,并且由于它在 with 调用中用作中间引用,因此从未分配给接口引用,并且其引用计数机制从未正确初始化。
要解决这个问题,您需要声明 IBuilder
接口并使用 class 返回该接口的函数来构造此类中间对象。
TDemo = class
public type
IBuilder = interface
function Generate: TDemo;
end;
TBuilder = class(TInterfacedObject, IBuilder)
public
function Generate: TDemo;
class function New: IBuilder;
end;
public
class procedure Using;
end;
class function TDemo.TBuilder.New: IBuilder;
begin
Result := TBuilder.Create;
end;
with TDemo.TBuilder.New.Generate do
...
为什么 TDemo.TBuilder 没有自动释放并产生内存泄漏? TDemo.TBuilder 应该自动释放,因为这是一个基于 IInterface
的 TInterfacedObject 对象type
TDemo = class
public type
TBuilder = class(TInterfacedObject)
public
function Generate: TDemo;
end;
public
class procedure Using;
end;
implementation
function TDemo.TBuilder.Generate: TDemo;
begin
Result := TDemo.Create;
// on finish this method, TDemo.TBuilder should be freed !
end;
class procedure TDemo.Using;
begin
with TDemo.TBuilder.Create.Generate do try
// use TDemo
finally
Free;
end;
end;
您有内存泄漏,因为 TBuilder.Create
returns 对象引用,并且由于它在 with 调用中用作中间引用,因此从未分配给接口引用,并且其引用计数机制从未正确初始化。
要解决这个问题,您需要声明 IBuilder
接口并使用 class 返回该接口的函数来构造此类中间对象。
TDemo = class
public type
IBuilder = interface
function Generate: TDemo;
end;
TBuilder = class(TInterfacedObject, IBuilder)
public
function Generate: TDemo;
class function New: IBuilder;
end;
public
class procedure Using;
end;
class function TDemo.TBuilder.New: IBuilder;
begin
Result := TBuilder.Create;
end;
with TDemo.TBuilder.New.Generate do
...