我已经实现了Generics.Defaults.TComparer来排序类型化的TList。但是,在调用Sort方法时,它会抛出异常“Stack overflow at ...”
为什么发生堆栈溢出错误?
// Declarations
TOrder = record
ID: Integer;
OrderDate: TDate;
end;
POrder = ^TOrder;
FOrderList: TList<POrder>;
TComparer_OrderDate = class(TComparer<POrder>)
public
function Compare(const a, b: POrder): Integer; override;
end;
function TComparer_OrderDate.Compare(const a, b: POrder): Integer;
begin
Result := 0;
if (a^.OrderDate> b^.OrderDate) then
Result := 1
else
Result := -1;
end;
// This code inside a button OnClick event:
FOrderList := TList<POrder>.Create;
FComparer_OrderDate := TComparer_OrderDate.Create;
FOrderList.Sort(FComparer_OrderDate); // <--- 'stack overflow' error.
答案 0 :(得分:7)
您的比较函数需要返回0才能获得相等性。像这样:
function TComparer_OrderDate.Compare(const a, b: POrder): Integer;
begin
if (a^.OrderDate > b^.OrderDate) then
Result := 1
else if (a^.OrderDate < b^.OrderDate) then
Result := -1
else
Result := 0;
end;
end;
使用TComparer<POrder>.Construct
制作比较器更容易。
FOrderList.Sort(
TComparer<POrder>.Construct(
function(const a, b: POrder): Integer
begin
if (a^.OrderDate > b^.OrderDate) then
Result := 1
else if (a^.OrderDate < b^.OrderDate) then
Result := -1
else
Result := 0;
end;
end
)
);
或使用默认日期时间比较器:
DateTimeComparer := TComparer<TDateTime>.Default;
FOrderList.Sort(
TComparer<POrder>.Construct(
function(const a, b: POrder): Integer
begin
Result := DateTimeComparer.Compare(a^.OrderDate, b^.OrderDate);
end
)
);
我没有编译任何这些,所以我希望会有一些小错误。