在容器之间移动对象并丢失接口

时间:2012-01-29 14:40:34

标签: delphi inheritance object interface

假设我们有界面I,对象O和容器sl

type
  rootInterface = Interface
  end;

  childOfRootInterface = interface(rootInterface)
  end;

  ObjectImplementsRootInterface = class(TObject, I)
  end;

  ObjectImplementsChildOfRootInterface = class(TOtherObject, I2);
  end;

var
  aStringList: TStringList;

假设sl已初始化。

如果我们这样做

aStringList.Items.AddObject('root', ObjectImplementsRootInterface );

然后我们不能做

ObjectImplementsRootInterface  := I(aStringList.Items.Objects([0]));

因为德尔福禁止这样做。所以尝试:

ObjectImplementsRootInterface  := TObject(aStringList.Items.Objects([0]));

但是,我们添加了childOfRootInterface,我们想要回childOfRootInterface,所以我们

ObjectImplementsChildOfRootInterface  := childOfRootInterface (sl.Items.Objects([0]));

但是ObjectImplementsChildOfRootInterfaceObjectImplementsRootInterface有不同的超级!

虽然它们支持相同的界面,但我们无能为力。

在java中你可以传递对象,只要它们支持接口,在java中它是可能的,所以现在经过所有这些规划;我能在德尔福做什么?

更新:更改了名称,但是示例可能已经超过我而赢了,找不到左右。

2 个答案:

答案 0 :(得分:1)

这是一个有效的代码示例:

program Project9054004;

{$APPTYPE CONSOLE}

uses
  Classes, SysUtils, Dialogs;

type  
  I = interface
  ['{6D39CF0A-839A-4DA3-B058-52E424702652}']
  end;

  O = class(TInterfacedObject, I)
  end;

var
  SL: TStrings;
  TempO: O;
  TempI: I;
begin
  ReportMemoryLeaksOnShutdown := True;

  SL := TStringlist.Create;
  try
    TempO := O.Create;
    SL.AddObject('a', TempO);

    if Supports(SL.Objects[0], I, TempI) then
    begin
      // use I
      TempI._AddRef;
      TempI._Release;
    end;

    ShowMessage(SL.Objects[0].ClassName);

  finally
    SL.Free;
  end;
end.

为避免硬类型转换,我使用GUID作为接口。

支持可用于安全测试并将对象分配给类型I的变量。请注意,类型名称在您的示例中有点令人困惑。

对象列表中的项目无法对界面进行严格的类型转换。

答案 1 :(得分:0)

简单地放弃了,并添加了另一个可以包含该XML的数据结构,并希望保留一个不能使用它们的Invariant。