关于局部变量的内存占用问题。
写了一个小软件。发现内存占用率会随着执行一个函数的次数而增加。
注释掉使用这行函数的代码内存就 很正常了
function SetBmpMon(Mapcode:string;x,y:Integer;MonName:string;Range,quantity;Bmpp:TBitmap):TBitmap;
var
Sx,Ex,Sy,Ey,i,j,k:Integer;
XList:TStringList;
YList:TStringList;
Can:Boolean;//用来标识该范围是不是全部都不能刷怪
bmp:TBitMap;
begin
bmp:=Tbitmap.create;
bmp:=bmpp;
can:=False;
sx:=x-Range;
ex:=x+Range;
sy:=y-Range;
ey:=y+Range;
if Sx < 1 then sx:=0;
if Ex > Bmp.Width-1 then ex:=Bmp.Width;
if Sy < 1 then sy:=0;
if Ey > Bmp.Height-1 then ey:=Bmp.Height;
Xlist:=TStringList.Create;
YList:=TStringList.create;
for i := sx to ex-1 do
begin
for j := sy to Ey-1 do
begin
if canwalk[i,j] then
begin
XList.Add(IntToStr(i));
YList.Add(IntToStr(j));
can:=True
end;
end;
end;
if can then
begin
while quantity <> 0 do
begin
k:=Math.RandomRange(0,XList.Count);
i:=StrToInt(XList[k]);
j:=StrToInt(YList[k]);
bmp.Canvas.Pixels[i,j]:=clRed;
bmp.Canvas.Pixels[i+1,j]:=clRed;
bmp.Canvas.Pixels[i-1,j]:=clRed;
bmp.Canvas.Pixels[i,j+1]:=clRed;
bmp.Canvas.Pixels[i,j-1]:=clRed;
bmp.Canvas.Pixels[i+1,j+1]:=clRed;
bmp.Canvas.Pixels[i-1,j-1]:=clRed;
bmp.Canvas.Pixels[i+1,j-1]:=clRed;
bmp.Canvas.Pixels[i-1,j+1]:=clRed;
MonName[i+1,j]:=name;
MonName[i-1,j]:=name;
MonName[i,j+1]:=name;
MonName[i,j-1]:=name;
MonName[i+1,j+1]:=name;
MonName[i-1,j-1]:=name;
MonName[i+1,j-1]:=name;
MonName[i-1,j+1]:=name;
MonName[i,j]:=name;
quantity:=quantity-1;
end;
end else
begin
while many <> 0 do
begin
i:=Math.RandomRange(0,bmp.Width);
j:=Math.RandomRange(0,bmp.Height);
if canwalk[i,j] then
begin
bmp.Canvas.Pixels[i,j]:=clRed;
bmp.Canvas.Pixels[i+1,j]:=clRed;
bmp.Canvas.Pixels[i-1,j]:=clRed;
bmp.Canvas.Pixels[i,j+1]:=clRed;
bmp.Canvas.Pixels[i,j-1]:=clRed;
bmp.Canvas.Pixels[i+1,j+1]:=clRed;
bmp.Canvas.Pixels[i-1,j-1]:=clRed;
bmp.Canvas.Pixels[i+1,j-1]:=clRed;
bmp.Canvas.Pixels[i-1,j+1]:=clRed;
MonName[i+1,j]:=name;
MonName[i-1,j]:=name;
MonName[i,j+1]:=name;
MonName[i,j-1]:=name;
MonName[i+1,j+1]:=name;
MonName[i-1,j-1]:=name;
MonName[i+1,j-1]:=name;
MonName[i-1,j+1]:=name;
MonName[i,j]:=name;
quantity:=quantity-1;
end;
end;
end;
Result:=Bmp;
end;
这行函数是传递进来一些数值,和一个全局变量的TBITMAP;
根据传递进来的数值在这张Tbitmap上画红点(模拟传奇私服刷怪)。
然后返回画好的图。
但是我发现。执行次数越多 内存占用就跟着上 就是不会掉下来。
最后就是 OUT Memeory。
不是说局部变量在函数结束后会就会被释放吗?
怎么越来越多呢!
[解决办法]
两个TStringList对象均未释放,另函数外部记得释放TBitMap对象。
[解决办法]
bmp:=Tbitmap.create; 这句多余,也造成内存泄漏。
[解决办法]
不是说局部变量在函数结束后会就会被释放吗?
——
对,但变量所引用的对象不会释放。比如XList,在函数结束后,他变量本身所占的4字节空间被回收,但是他引用的TStringList对象没释放,必须手动释放,如果不手动释放,对象会一直存在,直到进程结束。
[解决办法]
DISPOSE释放指针不释放对象,对象真正的析构函数为Destroy,但Destroy不安全,Free调用了Destroy且有保护机制,因此应用Free
[解决办法]
还有局部变量中自动释放的只是简单类型。。谁跟你说对象会自动释放了?!
[解决办法]
+1 free内部判断对象的引用是不是nil,如果不是nil就调用destroy