問題は、動的配列がクラスメンバーとして設定されている場合、Delphiによって内部的にどのように管理されるかです。それらは参照によってコピーまたは渡されますか?Delphi 10.3.3を使用。
このUpdateArray
メソッドは、配列から最初の要素を削除します。ただし、配列の長さは2のままです。このUpdateArrayWithParam
メソッドは、配列から最初の要素も削除します。ただし、配列の長さは正しく1に短縮されます。
ここにコードサンプルがあります:
interface
type
TSomeRec = record
Name: string;
end;
TSomeRecArray = array of TSomeRec;
TSomeRecUpdate = class
Arr: TSomeRecArray;
procedure UpdateArray;
procedure UpdateArrayWithParam(var ParamArray: TSomeRecArray);
end;
implementation
procedure TSomeRecUpdate.UpdateArray;
begin
Delete(Arr, 0, 1);
end;
procedure TSomeRecUpdate.UpdateArrayWithParam(var ParamArray: TSomeRecArray);
begin
Delete(ParamArray, 0, 1);
end;
procedure Test;
var r: TSomeRec;
lArr: TSomeRecArray;
recUpdate: TSomeRecUpdate;
begin
lArr := [];
r.Name := 'abc';
lArr := lArr + [r];
r.Name := 'def';
lArr := lArr + [r];
recUpdate := TSomeRecUpdate.Create;
recUpdate.Arr := lArr;
recUpdate.UpdateArray;
//(('def'), ('def')) <=== this is the result of copy watch value, WHY two values?
lArr := [];
r.Name := 'abc';
lArr := lArr + [r];
r.Name := 'def';
lArr := lArr + [r];
recUpdate.UpdateArrayWithParam(lArr);
//(('def')) <=== this is the result of copy watch value - WORKS
recUpdate.Free;
end;
Delete
手順のせいです。動的配列を再割り当てする必要があるため、その配列へのすべてのポインタを移動する必要があります。しかし、それはこれらのポインタの1つ、つまりあなたがそれに与えるものだけを知っています。