【问题标题】:store array of TPoint inside TObjectList在 TObjectList 中存储 TPoint 数组
【发布时间】:2013-03-27 22:57:05
【问题描述】:

我定义了一个 Objectlist 来存储几个 Polygons 作为 TFPolygon = 在这个 TObjectList 中的 TPoint 数组;但是使用我的 objectlist 的 add 功能,我得到一个访问冲突错误 :

type
  TFPolygon = array of TPoint;
  TFPolygonList = class(TObjectList)
  private
    procedure SetPolygon(Index: Integer; Value: TFPolygon);
    function GetPolygon(Index: Integer): TFPolygon;
  public
    procedure Add(p: TFPolygon);
    property Items[index: Integer]: TFPolygon read GetPolygon write SetPolygon; default;
  end;

implementation

procedure TFPolygonList.SetPolygon(Index: Integer; Value: TFPolygon);
begin
  inherited Items[Index] := Pointer(Value);
end;

function TFPolygonList.GetPolygon(Index: Integer): TFPolygon;
begin
  Result := TFPolygon(inherited Items[Index]);
end;

procedure TFPolygonList.Add(p: TFPolygon);
begin
  inherited Add(Pointer(p));
end;

我无法理解此代码示例中的错误?我可以只将类存储在 TObjectList 中,还是我存储 TPoints 数组的方法也有效?

【问题讨论】:

    标签: delphi


    【解决方案1】:

    您的方法无效。动态数组是托管类型。它们的生命周期由编译器管理。为此,您不能放弃它们是托管类型这一事实,这正是您所做的。

    您将动态数组转换为Pointer。此时,您已经对动态数组进行了新引用,但编译器并没有意识到这一点,因为 Pointer 不是托管类型。

    您有几个选项可以解决您的问题。

    1. 如果您使用的是现代 Delphi,请停止使用 TObjectList。而是使用Generics.Collections 中的通用类型安全容器。在您的情况下,TList<TFPolygon> 是您所需要的。因为这是编译时类型安全的,所以托管类型的所有生命周期都会得到处理。
    2. 如果您使用的是较旧的 Delphi,则可以将动态数组包装在一个类中。然后将这些类的实例添加到您的TObjectList。确保您的列表配置为拥有其对象。您完全可以在 TFPolygonList 的实现中进行封装,这将很好地封装事物。

    【讨论】:

    • 我所有的代码都被替换为 TFPolygonList = TList ;很酷的短版:-)
    • @user 是的,这听起来正是我们所需要的。我不知道我们在泛型之前是如何管理的!
    • @Runner 嗯,是的,在 Delphi 中实现的泛型确实会产生更大的代码。有趣的是,如果编译器更聪明,很多重复可以折叠在一起。 .net 实现就是这样做的。
    • 可悲的是,如果 Delphi 中的很多东西能做更多的规划并追求质量而不是数量和魅力,他们可能会更好。到目前为止,我从来没有遇到过可执行文件大小的问题,但它们可以得到更多优化。
    猜你喜欢
    • 2017-12-24
    • 1970-01-01
    • 2014-05-10
    • 2013-12-15
    • 1970-01-01
    • 1970-01-01
    • 2021-12-05
    • 2012-07-08
    • 1970-01-01
    相关资源
    最近更新 更多