System.GetMem 和 System.ReallocMem 有什么区别?
Delphi 2009 帮助中对 ReallocMem 的描述与 GetMem 的描述完全相同。 System.FreeMem 和 System.Dispose 怎么样
数组应该使用什么?
type
PMemberDataList = ^TMemberDataList;
TMemberDataList = array[0..MaxClassMembers -1] of PMemberData;
var
FItems: PMemberDataList;
begin
GetMem(FItems, Value * SizeOf(Pointer));
FreeMem(FItems);
end;
或
begin
ReallocMem(FItems, Value * SizeOf(Pointer));
Dispose(FItems);
end;
解决方案
根据人们的建议,我将 FItems 声明为记录类型,而不是指向记录的指针,将 TMemberDataList 声明为动态数组,将 SetLength 声明为(解除)分配数组,将 New/Dispose 声明为数据
type
PMemberDataList = ^TMemberDataList;
TMemberDataList = array of PMemberData;
var
Items: TMemberDataList;
Item: PMemberData;
// Add
begin
Setlength(Items, 1);
New(Item);
Items[0]:= Item
end;
// Remove
begin
Dispose(Items[0]);
Setlength(Items, 0);
end;
最佳答案
GetMem 始终分配内存,FreeMem 始终释放/释放内存,ReallocMem 可能会执行其中一项或两项,或两者兼而有之。事实上,如果使用得当,ReAllocMem 实际上是唯一需要的内存管理 API。如果您从 nil 指针开始,并以大小 > 0 调用 ReAllocMem,那么它的作用类似于 GetMem。如果您以 size = 0 调用 ReAllocMem,那么它的作用类似于 FreeMem。它真正“重新分配”内存的唯一时间是指针非零且大小 > 0 时。
New 和 Dispose 旨在与类型化指针一起使用,或者对于“old-skool”人员来说,旧的 Turbo Pascal 对象模型(旧的“对象”)语法。New 和 Dispose 还将确保任何类型化指针对托管类型的引用将正确初始化该类型。例如,给出以下内容:
type
PMyRec = ^TMyRec;
TMyRec = record
Name: string;
Value: Variant;
end;
var
Rec: PMyRec;
begin
New(Rec);
try
Rec.Name := 'TestValue';
Rec.Value := 100;
...
finally
Dispose(Rec);
end;
end;
New 和 Dispose 将确保记录的 Name 和 Value 字段正确初始化、最终确定或清理。 New和Dispose,在上面的情况下相当于:
GetMem(Rec, SizeOf(Rec^));
Initialize(Rec);
...
Finalize(Rec);
FreeMem(Rec);
对于您给出的示例,Gamecat 是正确的,您可能最好使用动态数组,因为它们可以更好地由编译器管理,并且它们还具有自己的固有长度。在您的示例中,您必须单独跟踪数组中的项目数,这样无论您在数组中传递什么位置,您还必须传递当前分配的长度。通过使用动态数组,所有信息都整齐地打包在一起。这将允许您通过简单地执行以下操作之一来迭代数组,而不管当前长度如何:
var
Member: TMemberData;
Items: array of TMemberData;
...
begin
SetLength(Items, Value);
for Member in Items do // iterate over each element in the array
...
for Low(Items) to High(Items) do // same as above only using std functions
...
end;
最后,您可能想要使用动态数组的另一个原因是,如果 TMemberData 包含字符串、变体、接口(interface)或其他“托管”类型,它们将被正确初始化和最终确定,而无需手动执行此操作。
关于delphi - GetMem x ReallocMem,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/569995/