[英]Memory leak, misuse of thread?
Im trying to use the threads for the first time, but cant tell why am i getting memory leak, cause of misuse of the thread, or cause im that stupid and forgot to free something, but at this point, i cant tell, which one (or both) is it.我第一次尝试使用线程,但不知道为什么我会出现内存泄漏,线程滥用的原因,或者导致我愚蠢而忘记释放某些东西,但在这一点上,我不知道是哪个(或两者)是它。
This is the procedure that is being called on click这是单击时调用的程序
procedure TmainForm.scrollFrameClick(item:TEquipmentItem; itemFrame:TitemFrame);
begin
item.fullImage:=itemFrame.itemImage.Picture.Graphic;
setCurrentSearchItem(item);
end;
Procedure that calling thread调用线程的过程
procedure TmainForm.setCurrentSearchItem(item:TEquipmentItem);
begin
if not(assigned(searchResultTable)) then
searchResultTable:=TItemHtmlTable.Create
else
begin
freeandnil(searchResultTable);
searchResultTable:=TItemHtmlTable.Create;
end;
if getDomTh<>nil then
if getDomTh.Finished then
begin
getDomTh.Terminate;
getDomTh.WaitFor;
FreeAndNil(getDomTh);
end
else
begin
getDomTh.WaitFor;
getDomTh.Terminate;
FreeAndNil(getDomTh);
end;
getDomTh:=TCreateDomThread.Create(false,'http://www.example.com/ru/items/'+inttostr(item.ID),searchResultTable.DomTree);
currentItemImage.Picture.Graphic:=item.fullImage;
itemNameLab.Caption:=item.ItemName;
itemTypeLab.Caption:=item.ItemTypeName;
itemSubtypeLab.Caption:=item.ItemSubtypeName;
/////////////////
// At this point i would call a thread and use the result from the "searchResultTable"
/////////////////
if getDomTh<>nil then
if getDomTh.Finished then
freeandnil(searchResultTable)
else
begin
getDomTh.WaitFor;
getDomTh.Terminate;
FreeAndNil(getDomTh);
freeandnil(searchResultTable);
end;
end;
This is the thread unit这是线程单元
unit threadUnit;
interface
uses System.Classes,System.SysUtils, parser;
type
TCreateDomThread = class(TThread)
private
pDomTree:TDomTree;
pUrl:string;
public
property tDomTree:TDomTree read pDomTree write pDomTree;
property tUrl:string read pUrl write pUrl;
constructor Create(suspended:boolean; Url:string; DomTree:TDomTree);
procedure Execute; override;
end;
implementation
uses main;
constructor TCreateDomThread.Create(suspended:boolean; Url:string; DomTree:TDomTree);
begin
tDomTree:=DomTree;
tUrl:=Url;
inherited Create(suspended);
end;
procedure TCreateDomThread.Execute;
begin
if Terminated then Exit;
mainForm.getDomTree(tUrl, tDomTree);
end;
end.
DomTree retrieval DomTree 检索
procedure TmainForm.getDomTree(url:string; outputDomTree:TDomTree);
var
HtmlTxt: string;
begin
try
HtmlTxt := IdHTTP1.Get(url);
if not outputDomTree.RootNode.RunParse(HtmlTxt) then
TThread.Queue(nil,procedure begin showmessage('Can'#39'tParse HTML!') end);
except
on E: Exception do
TThread.Queue(nil,procedure begin ShowMessage(E.ClassName + ' : ' + E.Message); end);
end;
end;
If you call for the click a couple of times, taskmanager shows that committed memory is always increasing.如果您多次调用单击,任务管理器会显示提交的内存始终在增加。 I had no luck with debugging that, any advise would be much appreciated.我没有调试成功,任何建议将不胜感激。
EDIT:编辑:
So there is a bunch of TDomTree
which are not being free, but i couldnt understand, from where, cause thread is destroyed as expected所以有一堆TDomTree
不是免费的,但我无法理解,从哪里,导致线程按预期被破坏
Delphi memory manager screenshot Delphi 内存管理器截图
EDIT 2: Found the error.编辑 2:发现错误。
So i found the issue.所以我发现了这个问题。 StringList
from the TDomTree
was referenced in thread that updated the ui.来自TDomTree
StringList
在更新 ui 的线程中被引用。 So therefore, when worker thread tried to destroy the searchResultTable
, its TDomTree
's StringList
could not be terminated, creating exception, so whole TDomTree
was not terminating.因此,当工作线程试图销毁searchResultTable
,其TDomTree
的StringList
无法终止,从而产生异常,因此整个TDomTree
并未终止。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.