How to free thread in delphi

I have a multi-threaded application, as I ask here . I want to end the thread and start a new one when the next method is called.

procedure TFRABData.RefreshDataset;
var
  GridUpdater: TGridUpdater;
begin
  if Assigned(updaterThread) and (updaterThread <> nil) then
  begin
    updaterThread.Terminate;
  end;
  GridUpdater := TGridUpdater.Create(True);
  GridUpdater.OwnerForm := Self;
  updaterThread := GridUpdater;
  GridUpdater.FreeOnTerminate := False;
  GridUpdater.Start;
  CodeSite.Send('RefreshDataset executed');
end

but when FreeOnTerminateset to True, I get an access violation, but when FreeOnTerminateset to False, I get a memory leak. How to free the thread?

+5
source share
3 answers

In addition to RRUZ's answer , so that it works with FreeOnTerminate = False:

Terminate just sets the flag, it does nothing.

Edit

  if Assigned(updaterThread) and (updaterThread <> nil) then 
  begin 
    updaterThread.Terminate; 
  end; 

to

  if Assigned(updaterThread) then 
  begin 
    updaterThread.Free; 
  end; 

Freewill subsequently cause Terminateand WaitForto eliminate a memory leak.

+7
source

Terminate(), WaitFor() Free() , :

procedure TFRABData.RefreshDataset; 
var 
  GridUpdater: TGridUpdater; 
begin 
  if Assigned(updaterThread) then 
  begin 
    updaterThread.Terminate; 
    updaterThread.WaitFor; 
    FreeAndNil(updaterThread); 
  end; 
  GridUpdater := TGridUpdater.Create(True); 
  GridUpdater.OwnerForm := Self; 
  GridUpdater.Start; 
  updaterThread := GridUpdater; 
  CodeSite.Send('RefreshDataset executed'); 
end;
+9
  • avoid having to start a suspended thread
  • modify the constructor TThreadto get the OwnerForm parameter
  • set the value of FreeOnTerminate in the constructor of your thread.
  • Run TThread in a non-paused state.

something like that.

  TGridUpdater = class(TThread)
  private
    FOwnerForm: TForm;
  public
    constructor Create(OwnerForm : TForm); overload;
    destructor Destroy; override;
    procedure Execute; override;
  end;

constructor TGridUpdater.Create(OwnerForm: TForm);
begin
  inherited Create(False);
  FreeOnTerminate := True;
  FOwnerForm:=OwnerForm;
end;

destructor TGridUpdater.Destroy;
begin

  inherited;
end;

procedure TGridUpdater.Execute;
begin
  //your code goes here

end;

Now you can create your Tthread this way

GridUpdater:=TGridUpdater.Create(Self); //Just set it and forget it
+5
source

All Articles