Delphi动态数组引用计数

时间:2017-08-30 11:02:59

标签: delphi

我决定使用

而不是使用geneirc TList<integer>
TSolutions = array of integer;

然后:

function TEuclidMod.gcdExtended(p, q: integer): TSolutions;
var tmpArr: TSolutions;
begin

 SetLength(tmpArr, 3);

 if (q = 0) then
  begin
   tmpArr[0] := p;
   tmpArr[1] := 1;
   tmpArr[2] := 0;
  end
 else
  begin
   vals := gcdExtended(q, modulo(p,q));
   tmpArr[0] := vals[0];
   tmpArr[1] := vals[2];
   tmpArr[2] := vals[1] - vals[2]*floor(p/q);
  end;

 Result := tmpArr;

end;

变量vals: TSolutions;在类中声明为private,在构造函数内部我设置了它的长度。

我已经在docwiki上看到动态数组被重新计算,所以我不必担心它们的生命周期。确定我写了:

constructor TEuclidMod.Create;
begin

 SetLength(vals, 3);

end;

destructor TEuclidMod.Destroy;
begin

 vals := nil;
 inherited;

end;

到目前为止,这应该没问题; vals属于该类,我可以在类的破坏中释放它。那么tmpArr呢?

我的功能正常。 tmpArr是本地的,然后我调用SetLength,我给他一个长度:如果我没错,这就是在堆上创建数组。但是当我使用Result := tmpArr返回时,由于函数超出范围,它不会被删除(tmpArr)吗?我不想回复悬挂的指针或别的东西!我需要确保它没有被释放。

我想我是安全的,因为它是一个函数,它返回一个TSolution,所以引用计数应至少为1。这是确切的吗?基本上:即使它是本地的,它是否正确返回?

但是从我在SO上找到的,在这种情况下

procedure test;
var a: TSolution;
begin

 SetLength(a, 7);
 //do something

end;

当程序超出范围时,a总是被释放!

1 个答案:

答案 0 :(得分:7)

动态数组是引用计数的。不要担心他们的记忆管理 - 只需使用它们;那是什么参考计数。您不必在析构函数中nil类字段。当对象被销毁时,编译器将删除它们的引用计数。

  

但是当我带着Result返回时:= tmpArr没有被删除(tmpArr)因为函数超出了范围?

嗯,不,因为您已经通过将数组分配给Result来返回数组,并且可能是调用者依次将结果分配给新变量。除非调用者还没有将函数结果分配给新变量,否则引用计数自然会保持至少为一。