[教程]如果在 Delphi 中重载父类重载的接口中的某个非虚函数

好吧,这个问题可能够无聊,反正父类已经实现了,为啥不用父类的一类的问题就不要问了,反正这个事也没啥可争论的,只是告诉大家一种关于接口的写法。

我们都知道 Delphi 中接口对象一般从 TInterfacedObject 继承,但 QueryInterface 函数却不是虚函数,所以想重载是无门的,为此 QPlugins 自己重新实现了 TQInterfacedObject 来替代它。但实际上还有一种办法,可以让你重载它,那就是让你的子类重新继承下父类已经实现的接口(如IInterface),并且实现要重载的函数。示例如下:

type
  IObject = interface
    ['{ADB32A65-BACF-462C-8F76-E589A6CE27E9}']
    function TypeName: String;
  end;

  TTestObject = class(TInterfacedObject, IObject,IInterface)
    function TypeName: String;
  public
    function QueryInterface(const IID: TGUID; out Obj): HResult; stdcall;
  end;

procedure TForm2.Button1Click(Sender: TObject);
var
  AObj:IInterface;
begin
AObj:=TTestObject.Create;
ShowMessage((AObj as IObject).TypeName);
end;

{ TTestObject }

function TTestObject.QueryInterface(const IID: TGUID; out Obj): HResult;
begin
if IID=IObject then
  begin
  IObject(Obj):=Self;
  Result:=0;
  end
else
  Result:=QueryInterface(IID,Obj);
end;

function TTestObject.TypeName: String;
begin
  Result := ClassName;
end;

如果你在 TTestObject.QueryInterface 中设置断点,你会发现竟然能断断断断下来了,证明重载是生效的。而你没有重载的接口函数依然使用父类的实现,而这正是我们要的东西。

分享到: