Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Algorithmen, Datenstrukturen und Klassendesign (https://www.delphipraxis.net/78-algorithmen-datenstrukturen-und-klassendesign/)
-   -   Vererbung bei Implementierung eines Interfaces (https://www.delphipraxis.net/197058-vererbung-bei-implementierung-eines-interfaces.html)

bernhard_LA 14. Jul 2018 23:17

Vererbung bei Implementierung eines Interfaces
 
ich will die Funktionen eines Interfaces über verschiedene Klassen implementieren.

Delphi-Quellcode:
TMyClassA = class ( TInterfacedObject, IMyLibrary);
   ....
   ....
end;
die verschiedenen Klassen haben eine identische Funktionalität und einen Teil der eben unterschiedlich implementiert wird.
Ist es Möglich eine Verberbung auf Seiten der Interface Implementierung einzuführen ?


Delphi-Quellcode:
TMyClassRoot = class ();
   ....
   ....
end;


TMyClassA = class ( TInterfacedObject, IMyLibrary, TMyClassRoot);
   ....
   ....
end;


TMyClassB = class ( TInterfacedObject, IMyLibrary, TMyClassRoot);
   ....
   ....
end;
nur haben diese Ansätze leider nicht funktioniert .....

Aviator 14. Jul 2018 23:29

AW: Vererbung bei Implementierung eines Interfaces
 
Ich bin mir gerade nicht mehr ganz sicher (und kann es leider auch nicht ausprobieren) ob man Interface Methoden als
Delphi-Quellcode:
virtual;
deklarieren kann. Wenn ja, dann könntest du es so ausprobieren:

Delphi-Quellcode:
IMyInterface = interface
['{someGUID}']
 
  procedure MyFirstProcedure; // <-- Eventuell hier ein virtual falls der Compiler meckert und hier ein virtual erlaubt ist
end;

TMyClass = class(TInterfacedObject, IMyInterface)
  private
    procedure MyFirstProcedure; virtual;
end;

TMyFirstDerivedClass = class(TMyClass)
  private
    procedure MyFirstProcedure; override;
end;

TMySecondDerivedClass = class(TMyClass)
  private
    procedure MyFirstProcedure; override;
end;
Wenn nicht, dann könntest du es auch so lösen. Kommt eben darauf an, ob ein Teil der Interface Methoden gleich ist und ein weiterer Teil sich unterscheidet:

Delphi-Quellcode:
IMyInterface = interface
['{someGUID}']
 
  procedure MyFirstProcedure;
end;

TMyClass = class(TInterfacedObject)
  private
    procedure MyFirstProcedure; virtual;
end;

TMyFirstDerivedClass = class(TMyClass, IMyInterface)
  private
    procedure MyFirstProcedure; override;
end;

TMySecondDerivedClass = class(TMyClass, IMyInterface)
  private
    procedure MyFirstProcedure; override;
end;

jaenicke 15. Jul 2018 06:02

AW: Vererbung bei Implementierung eines Interfaces
 
Man kann virtuelle Methoden für ein Interface benutzen und diese auch überschreiben.

Nur im Interface selber kann man virtual usw. natürlich nicht nutzen, da das Interface ja nur die vorhandene Implementierung nutzt, egal wie diese deklariert ist.

bernhard_LA 15. Jul 2018 08:48

AW: Vererbung bei Implementierung eines Interfaces
 
bin mir gar nicht sicher ob ich override & virtual überhaupt benötige - das verschieben von gemeinsamen Funktionen in eine Root Klasse scheint zu funktionieren


Delphi-Quellcode:
IMyInterface = interface
['{someGUID}']
  procedure MySharedProcedure;
  procedure MyFirstProcedure;
end;

TMyClass = class(TInterfacedObject)
  private
    procedure MySharedProcedure;
end;

TMyFirstDerivedClass = class(TMyClass, IMyInterface)
  private
    procedure MyFirstProcedure;
end;

TMySecondDerivedClass = class(TMyClass, IMyInterface)
  private
    procedure MyFirstProcedure;
end;

himitsu 15. Jul 2018 09:46

AW: Vererbung bei Implementierung eines Interfaces
 
Die Implementation der letzten Ableitung, in welcher das Interface angegeben wurde, wird genommen.

Interface nur beim Vorfahren mit Virtual+Override (die Methoden überschreiben)
oder Interface mehrmals eingebunden geht nur auch ohne. (hier ist dann quasi das Inferface überschrieben, aber durch Method-Override würde das natürlich umgangen)

Aviator 15. Jul 2018 13:28

AW: Vererbung bei Implementierung eines Interfaces
 
Eine andere Methode wäre ein gemeinsames Basis-Interface. Und in den abgeleiteten Klassen jeweils ein weiteres Interface mit den speziellen Methoden für diese Klasse. Dann kann mit
Delphi-Quellcode:
Supports()
geprüft werden um welches Interface es sich handelt.

Schokohase 15. Jul 2018 13:44

AW: Vererbung bei Implementierung eines Interfaces
 
Als weitere Möglichkeit
Delphi-Quellcode:
IMyInterface = interface
  ['{934A8DAD-87C1-4780-8865-A9BD9CF5DFC8}']
  procedure MySharedProcedure;
  procedure MyFirstProcedure;
end;

TShared = class
public
  procedure MySharedProcedure;
end;

TMyFirstImpl = class(TInterfacedObject, IMyInterface)
private
  FShared: TShared;
protected
  property Shared: TShared read FShared implements IMyInterface;
  procedure MyFirstProcedure;
public
  constructor Create;
  destructor Destroy; override;
end;

{ TShared }

procedure TShared.MySharedProcedure;
begin
  // add some code
end;

{ TMyFirstImpl }

constructor TMyFirstImpl.Create;
begin
  inherited;
  FShared := TShared.Create;
end;

destructor TMyFirstImpl.Destroy;
begin
  FShared.Free;
  inherited;
end;

procedure TMyFirstImpl.MyFirstProcedure;
begin
  // add some code
end;

Uwe Raabe 15. Jul 2018 14:26

AW: Vererbung bei Implementierung eines Interfaces
 
Folgendes könnte unter bestimmten Umständen auch gehen und erzwingt nicht die Implementierung in der Basisklasse. Damit lässt es sich auch in bestehende Vererbungshierarchien einbinden. Klappt aber nur, wenn die Methoden weitestgehend autark sind.
Delphi-Quellcode:
// implementiert
TMyClassRoot = class ();
  procedure MySharedProcedure;
end;

IMyLibrary = interface
  procedure MySharedProcedure;
  procedure MyFirstProcedure;
end;


TMyClassA = class ( TInterfacedObject, IMyLibrary);
private
  FMyRoot: TMyClassRoot; // im Create erstellen und Destroy freigeben
protected
  MyRoot: TMyClassRoot read FMyRoot implements IMyLibrary; // was in TMyClassRoot fehlt, liefert diese Klasse nach
  procedure MyFirstProcedure;
end;


TMyClassB = class ( TInterfacedObject, IMyLibrary);
private
  FMyRoot: TMyClassRoot; // im Create erstellen und Destroy freigeben
protected
  MyRoot: TMyClassRoot read FMyRoot implements IMyLibrary; // was in TMyClassRoot fehlt, liefert diese Klasse nach
  procedure MyFirstProcedure;
end;


Alle Zeitangaben in WEZ +1. Es ist jetzt 06:00 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