В Delphi можно привязать интерфейс к объекту, который его не реализует

Я знаю, что в Delphi XE2 есть новый TVirtualInterface для создания реализаций интерфейса во время выполнения. К сожалению, я не использую XE2, и мне интересно, какие хакеры используются для подобных действий в старых версиях Delphi.

Допустим, у меня есть следующий интерфейс:

  IMyInterface = interface
  ['{8A827997-0058-4756-B02D-8DCDD32B7607}']
    procedure Go;
  end;

Можно ли выполнить привязку к этому интерфейсу во время выполнения без помощи компилятора?

TMyClass = class(TObject, IInterface)
public
  function QueryInterface(const IID: TGUID; out Obj): HResult; stdcall;
  function _AddRef: Integer; stdcall;
  function _Release: Integer; stdcall;
  procedure Go; //I want to dynamically bind IMyInterface.Go here
end;

Я пробовал простое жесткое приведение:

var MyInterface: IMyInterface;
begin
  MyInterface := IMyInterface(TMyClass.Create);
end;

, но компилятор предотвращает это.

Затем я попробовал преобразовать как , и он, по крайней мере, скомпилировал:

MyInterface := TMyClass.Create as IMyInterface;

Итак, я полагаю, что ключ в том, чтобы получить QueryInterface , чтобы вернуть действительный указатель на реализацию интерфейса. запрашивается. Как мне создать его во время выполнения?

Я копался в System.pas, поэтому я хотя бы смутно знаком с тем, как GetInterface , GetInterfaceEntry и InvokeImplGetter работает. (к счастью, Embacadero решил оставить исходный код pascal вместе с оптимизированной сборкой). Возможно, я неправильно это читаю, но похоже, что могут быть записи интерфейса со смещением нуля, и в этом случае есть альтернативный способ назначения интерфейса с помощью InvokeImplGetter .

Моя конечная цель - смоделировать некоторые возможности динамических прокси и имитаторов, доступных на языках с поддержкой отражения. Если я смогу успешно выполнить привязку к объекту, который имеет те же имена методов и сигнатуры, что и интерфейс, это будет большим первым шагом. Возможно ли это, или я лаю не на то дерево?

10
задан Kenneth Cochran 21 September 2011 в 16:13
поделиться