Reputation: 13
Why is TDemo.TBuilder is not automatically freed and producing a memory leak ? TDemo.TBuilder should be freed automatically, as this is a TInterfacedObject object based on IInterface
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;
Upvotes: 1
Views: 292
Reputation: 28517
You have memory leak because TBuilder.Create
returns object reference and since it is used as intermediate reference in with call it was never assigned to interface reference and its reference counting mechanism was never properly initialized.
To solve this, you need to declare IBuilder
interface and use class function returning that interface for constructing such intermediate object.
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
...
Upvotes: 6