Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Object-Pascal / Delphi-Language (https://www.delphipraxis.net/32-object-pascal-delphi-language/)
-   -   Interface-Vererbung einer privaten Klasse (https://www.delphipraxis.net/166103-interface-vererbung-einer-privaten-klasse.html)

normancz 30. Jan 2012 13:48

Delphi-Version: 2007

Interface-Vererbung einer privaten Klasse
 
Hallo,
ich habe hier eine private Klasse, welche nur per Interface erreichbar sein soll um sie später per Factory/DI einfach auszutauschen:
Delphi-Quellcode:
unit UnitA;

interface

type
  IFoo = interface(IInterface)
  ['{90CA22A8-ACC3-4EF8-8E41-3C1B7EF755E3}']
    procedure Foo; stdcall;
  end;

function GetFooFromFactoryWithDI: IFoo;

implementation

type
  TFoo = class(TInterfacedObject, IFoo)
  protected
    procedure Foo; stdcall;
  end;

...
Nun möchte ich diese Klasse in einer anderen Unit noch erweitern. Dies klappt allerdings nicht so, wie ich es mir vorstelle:
Delphi-Quellcode:
unit UnitB;

interface

uses
  UnitA;

type
  IBar = interface(IFoo)
  ['{ABCDF8A2-646E-48A7-8B80-DAAE3244281B}']
    procedure Bar; stdcall;
  end;

function GetBarFromFactoryWithDI: IBar;

implementation

type
  TBar = class(TInterfacedObject, IBar)
  private
    fMasterFoo: IFoo;
  protected
    procedure Bar; stdcall;
  public
    property MasterFoo: IFoo read fMasterFoo implements IFoo;
  end;

...
Ich dachte eigentlich, dass ich per implements das Foo-Interface einfach einbinden kann, aber Delphi will es dann auch in der Klassendefinition angegeben haben. Nur danach wird Foo aus IBar vermisst.

Was habe ich da übersehen, oder ist so eine Vererbung nicht möglich?

Edit:
Jetzt bin ich einen Schritt weiter gekommen, welcher zumindest compiliert aber noch nicht außerhalb des Beispielprojekts getestet wurde:
Delphi-Quellcode:
  TNewFoo = class(TInterfacedObject, IFoo)
  private
    fMasterFoo: IFoo;
  public
    property MasterFoo: IFoo read fMasterFoo implements IFoo;
  end;

  TBar = class(TNewFoo, IBar)
  protected
    procedure Bar; stdcall;
  end;
Gibt es eine elegantere Lösung ohne die zweit-Klasse?

Bye,
Norman

shmia 30. Jan 2012 14:10

AW: Interface-Vererbung einer privaten Klasse
 
Vererbung von Interfaces ist immer mit Vorsicht zu geniessen.
Aber man kann ja mehrere Interfaces pro Klasse implementieren:
Delphi-Quellcode:
  IFoo = interface(IInterface)
  ['{90CA22A8-ACC3-4EF8-8E41-3C1B7EF755E3}']
    procedure Foo; stdcall;
  end;

  IBar = interface(IInterface)
  ['{ABCDF8A2-646E-48A7-8B80-DAAE3244281B}']
    procedure Bar; stdcall;
  end;

type
  TFoo = class(TInterfacedObject, IFoo, IBar)
  protected
    procedure Foo; stdcall;
    procedure Bar; stdcall;
  end;


var
  x : IFoo;
  b : IBar;
begin
  x := TFoo.Create();
  x.Foo;

  b := x as IBar; // bei älterem Delphi muss hier die Supports-Funktion verwendet werden
  b.Bar;

himitsu 30. Jan 2012 14:39

AW: Interface-Vererbung einer privaten Klasse
 
Du willst ja ein Objekt haben, welches mehrere Interfaces implementiert.
Ein Interface ist nur die Schnittstelle. IFoo kennt also keinerlei funktionalen Code und erst Recht nicht den von TFoo, da es TFoo garnicht kennt.

TBar ist ein eigenes Objekt und das kennt TFoo nicht, also kann es auch nicht die Methoden von IBar automatisch bereitstellen.

Entweder du leitest TBar von TFoo ab.
Oder du mußt IFoo innerhalb des TBar laden/erstellen, die Methoden von IFoo auch noch in dein TBar implementieren und die Aufrufe zum eingebundenen IFoo weiterleiten.

Oder du implementierst alles in TBar nochmals neu, welches von dem unzugänglichen TFoo benötigt wird.


Alle Zeitangaben in WEZ +1. Es ist jetzt 05:32 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz