Interface/ Klasse oder Vererbung?

Die Objektorientierung mit ABAP®: Vererbung, Dynamische Programmierung, GUI Controls (u.a. ALV im OO).
14 Beiträge • Seite 1 von 1
14 Beiträge Seite 1 von 1

Interface/ Klasse oder Vererbung?

Beitrag von ewx (Top Expert / 4848 / 312 / 642 ) »
Hallo zusammen!

Ich stehe mal wieder auf dem OO-Schlauch...

Ich habe mehrere Objekte die alle die gleiche Funktionalität bekommen sollen: IS_MODIFIED?
Dafür brauche ich die Methoden SET_MODIFIED und IS_MODIFIED sowie mindestens ein Attribut.

Variante 1: Interface
Ich definiere ein Interface und definiere die Methoden. Das Interface binde ich dann in die benötigten Klassen ein. Allerdings muss ich die Implementierung dann in jeder Klasse vornehmen. Das möchte ich nicht.

Variante 2: Vererbung
Ich definiere eine Basisklasse mit den beiden Methoden und lasse die Objekt-Klassen von dieser Klasse erben. Dann muss ich die Implementierung nur einmal in der Basis-Klasse vornehmen. Das möchte ich aber auch nicht, weil "MODIFIED" ja keine Hauptklasse in dem Sinne ist. Wenn ich das einmal gemacht habe, dann kann ich keine weiteren Funktionen nach diesem Muster einbauen.

Variante 3: (Interface ->) Attribut -> Klasse
Ich definiere eine Klasse mit den beiden Methoden und dem Kennzeichen "modified". Diese Klasse binde ich entweder direkt in meine Objekt-Klassen ein.
Nachteile:
- Das modified-Objekt muss instanziiert werden. Nicht schlimm aber auch nicht schön.
- Der Zugriff erfolgt immer über Attribut->Methode. Die Methode gehört also irgendwie nicht wirklich zu der Objektklasse...

Variante 4: Modified-Controller
Ich erstelle einen Controller in dem ich mir mittels ZCL_HELPER_MODIF=>SET_MODIFIED( Objekt-Klasse ) merke, welche Objekte geändert wurden.
Mit IS_MODIFIED( Objekt-Klasse ) bekäme ich einfach wieder raus, ob das Objekt geändert wurde.
oder es erfolgt ein RAISE EVENT i_am_modified( me ).

Herausforderung:
Ich habe ein Hauptobjekt mit Unterobjekten:
Hauptobjekt z.B. LIEFERBELEG
Unterobjekte z-B.
- Texte
- Packstücke

Wenn "Texte" geändert wurden, dann meldet das Texte-Objekte, dass es geändert wurde.
Lieferbeleg-Objekt muss natürlich seine Objekte nach Änderungen abfragen, das ist klar.

Es sollte also eine einheitliche Schnittstelle nach Außen geben (Interface) mit der Möglichkeit, die Funktionalität selbst in einem eigenen Objekt zu haben.
Das ganze sollte zudem nur lose an das Objekt gekoppelt sein. Ich möchte gegebenenfalls noch andere generische Funktionalitäten anbinden, wie z.B. "HASH-Wert des Objektes ermitteln", "Bearbeitung auf 'Anzeige' setzen" oder ähnliches.

Hat jemand eine gute Idee/ Entwurfsmuster dafür?

Gruß und schönes WE!

gesponsert
Stellenangebote auf ABAPforum.com schalten
kostenfrei für Ausbildungsberufe und Werksstudenten


Re: Interface/ Klasse oder Vererbung?

Beitrag von black_adept (Top Expert / 4090 / 127 / 940 ) »
Hallo Enno,

in Variante (1) sagst du zwar, dass du keine Implementierung in jeder Klasse vornehmen willst, andererseits bist du in (3) bereit das von dir angesprochene Interfaceattribut zu instanziieren, was ja im Grunde der Implementierung der Instanzmethode entspricht.

Somit nimm eine Kombination von (1) und (3). Benutze das Interface, weil es ja genau das ist was du haben willst. Wenn hingegen die Funktionalität des Interfaces hinreichend komplex ist, so dass du nicht das gesamte Coding in alle implementierenden Klassen (redundant) kopieren willst verwende die (3)-Technik aber ohne Interfaceattribut. Nimm dir hier ein nicht-öffentliches Attribut, welches eine Referenz auf eine Klasse ist, die das Verhalten des Interface vollständig implementiert und sonst halt nichts macht. Dann brauchst du bei der Implementierung des Interfaces nur die Interfacemethoden auf die gleichnamigen Methoden des nicht-öffentlichen Attributs durchschleifen.
Für den Beispiel sähe dann das Coding der Implementierung der Methoden SET_MODIFIED und GET_MODIFIED etwa so aus ( auf das Interfaceattribut solltest du hier verzichten, da du ja eine IS_MODIFIED-Methode hast - du musst dich halt entscheiden ob du auf die Eigentschaft via Attribut oder via GETTER-Methode zugreifen willst )

Code: Alles auswählen.

METHOD is_modified.
  rv_is_modified = non_public_attribute->is_modified( ).
ENDMETHOD.
METHOD set_modified.
  non_public_attribute->set_modified( ).
ENDMETHOD.

Folgende Benutzer bedankten sich beim Autor black_adept für den Beitrag:
ewx

live long and prosper
Stefan Schmöcker

email: stefan@schmoecker.de

Re: Interface/ Klasse oder Vererbung?

Beitrag von black_adept (Top Expert / 4090 / 127 / 940 ) »
Hallo Enno,
ewx hat geschrieben:Hallo zusammen!
Variante 2: Vererbung
Ich definiere eine Basisklasse mit den beiden Methoden und lasse die Objekt-Klassen von dieser Klasse erben. Dann muss ich die Implementierung nur einmal in der Basis-Klasse vornehmen. Das möchte ich aber auch nicht, weil "MODIFIED" ja keine Hauptklasse in dem Sinne ist. Wenn ich das einmal gemacht habe, dann kann ich keine weiteren Funktionen nach diesem Muster einbauen.
Eigentlich schließen sich (1) und (2) ja nicht aus, sondern (2) wäre ein übliches Vorgehen um den angesprochenen Nachteil von (1) überwinden. Ich kann deine Bedenken nur dann teilen, wenn du in diversen Objekten verschiedene Interfaces implementieren willst und du wegen nicht vorhandener Mehrfachvererbung dann eine überfrachtete Basisklasse hast, die alle in Frage kommenden Interfaces implementiert und man an den Unterobjekten nicht mehr direkt sehen kann, ob sie nun das Interface selber benötigen oder nur durch die Ableitung von der Basisklasse schon mal "für den Fall dass du es brauchst" übergestülpt bekommen haben.
Um dieses Dilemma zu lösen würde ich wahrscheinlich wie folgt vorgehen:

In Variante (1) sagst du zwar, dass du keine Implementierung in jeder Klasse vornehmen willst, andererseits bist du in (3) bereit das von dir angesprochene Interfaceattribut zu instanziieren, was ja im Grunde der Implementierung der Instanzmethode entspricht.

Somit nimm eine Kombination von (1) und (3). Benutze das Interface, weil es ja genau das ist was du haben willst. Wenn hingegen die Funktionalität des Interfaces hinreichend komplex ist, so dass du nicht das gesamte Coding in alle implementierenden Klassen (redundant) kopieren willst verwende die (3)-Technik. Nimm dir hier ein nicht-öffentliches Attribut, welches eine Referenz auf eine Klasse ist, die das Verhalten des Interface vollständig implementiert und sonst halt nichts macht. Dann brauchst du bei der Implementierung des Interfaces nur die Interfacemethoden auf die gleichnamigen Methoden des nicht-öffentlichen Attributs durchschleifen.
Für den Beispiel sähe dann das Coding der Implementierung der Methoden SET_MODIFIED und GET_MODIFIED etwa so aus ( auf das Interfaceattribut solltest du hier verzichten, da du ja eine IS_MODIFIED-Methode hast - du musst dich halt entscheiden ob du auf die Eigentschaft via Attribut oder via GETTER-Methode zugreifen willst )

Code: Alles auswählen.

METHOD is_modified.
  rv_is_modified = non_public_attribute->is_modified( ).
ENDMETHOD.
METHOD set_modified.
  non_public_attribute->set_modified( ).
ENDMETHOD.

Folgende Benutzer bedankten sich beim Autor black_adept für den Beitrag:
ewx

live long and prosper
Stefan Schmöcker

email: stefan@schmoecker.de

Re: Interface/ Klasse oder Vererbung?

Beitrag von erp-bt (Specialist / 163 / 4 / 21 ) »
Hi,

also ich mache das in solchen Fällen gerne so, dass ich für das Interface noch eine abstrakte Klasse definiere. Die abstrakte Klasse implementiert dann das Interface auch abstrakt. Das hat für mich bisher noch jeden Fall abgedeckt den ich gebraucht habe, mit dem Vorteil das man gemeinsame Methoden/Attribute in der abstrakten Klasse definieren/implementieren kann. Hier mal ein Auszug als Basis des Decorator-Pattern. Ich hoffe es wird deutlich (möchte nicht zu viel Coding hier reinkopieren). Man beachte das das Attribut DECORATEE in jeder implementieren Klasse als Instanzattribut existiert, da Protected.

Code: Alles auswählen.

interface IF_CSP_DOC_MAKER
  public .

  methods CREATE
    importing
      !I_SOURCE_ITEM type S_SOURCE_ITEM
    changing
      !C_ACC_DOCUMENT type S_ACC_DOCUMENT .
endinterface.

class CL_DOC_MAKER_ABS definition
  public
  abstract
  create public .

public section.

  interfaces IF_CSP_DOC_MAKER
      all methods abstract . "<-- Interface abstrakt definieren

  methods SET_DECORATEE
    importing
      !I_DOC_WORKER type ref to IF_CSP_DOC_MAKER .

protected section.

  data DECORATEE type ref to IF_CSP_DOC_MAKER .

private section.

ENDCLASS.

class CL_DOC_MAKER_A definition
  public
  inheriting from CL_DOC_MAKER_ABS
  final
  create public .

public section.

  methods IF_CSP_DOC_MAKER~CREATE
    redefinition .

protected section.
private section.
ENDCLASS.

Viele Grüße, Tapio

Folgende Benutzer bedankten sich beim Autor erp-bt für den Beitrag:
ewx

...entwickelnder Berater...beratender Entwickler

Re: Interface/ Klasse oder Vererbung?

Beitrag von ewx (Top Expert / 4848 / 312 / 642 ) »
Dass irgendwas mit "abstrakt" kommt, damit hatte ich schon gerechnet... ;)
Verstanden habe ich es aber leider nicht...
Wie wird *CSP_DOC_MAKER denn verwendet?
Wo ist das konkrete Coding?

Re: Interface/ Klasse oder Vererbung?

Beitrag von black_adept (Top Expert / 4090 / 127 / 940 ) »
@Tapio,

deine Vorgehensweise benutze ich auch häufig. Aber Enno sagt ja, dass er letztendlich mehrere "Decorators" in seinen Objekten haben kann. Falls alle Objekte alle Decorators benötigen ist deine Vorgehensweise wohl die Anzuratende. Aber nicht, wenn die Objekte nur eine Auswahl ( und nicht alle die gleiche Auswahl ) der "Decorators" haben sollen. Denn da SAP keine Mehrfachvererbung kennt bekommt man so leider immer völlig überladene Kinder der abstrakten Implementierung.
live long and prosper
Stefan Schmöcker

email: stefan@schmoecker.de

Re: Interface/ Klasse oder Vererbung?

Beitrag von ewx (Top Expert / 4848 / 312 / 642 ) »
Der Decorator ist vom Prinzip ja passend, da es eben nicht auf den "Decorator" ankommt, sondern auf die "Deko-Zutaten". Und das würde ja schon passen.
Ich habe aber eben nicht verstanden, wie... :--(

Re: Interface/ Klasse oder Vererbung?

Beitrag von erp-bt (Specialist / 163 / 4 / 21 ) »
Hi,

Es geht ja gar nicht so sehr um den Decorator, sondern um die Möglichkeit Interfaces abstrakt in einer abstrakten Klasse zu definieren, die dann in der jeweiligen konkreten Implementierung ausprogrammiert werden, aber gleichzeitig Attribute und Methoden der abstrakten Klasse zu nutzen, damit man eben nicht alles konkret in der "Kind"-Klasse implementieren muss. Das "Decoratee"-Attribut ist ja immer eine konkrete Instanz. Und natürlich können auch mehrere Attribute existieren.

Mehrfachvererbung gibt's nicht, aber man kann mehrere Interfaces implementieren. Es würde ja vermutlich auch funktionieren 2 Interfaces zu definieren und in der abstrakten Klasse eines auch abstrakt zu definieren und das andere Interface konkret in der abstrakten Klasse zu implementieren. Das habe ich aber selbst noch nicht ausprobiert. Ich bin bisher immer so zurecht gekommen.

Viele Grüße, Tapio
...entwickelnder Berater...beratender Entwickler

Re: Interface/ Klasse oder Vererbung?

Beitrag von hausi (ForumUser / 56 / 11 / 1 ) »
Hi,
Es geht ja gar nicht so sehr um den Decorator, sondern um die Möglichkeit Interfaces abstrakt in einer abstrakten Klasse zu definieren, die dann in der jeweiligen konkreten Implementierung ausprogrammiert werden, aber gleichzeitig Attribute und Methoden der abstrakten Klasse zu nutzen, damit man eben nicht alles konkret in der "Kind"-Klasse implementieren muss. Das "Decoratee"-Attribut ist ja immer eine konkrete Instanz. Und natürlich können auch mehrere Attribute existieren.
ich habe ehrlich gesagt das Problem nicht 100% erfassen können - dafür bin ich glaub ich noch zu grün hinter den Öhrchen....

Aber grundsätzlich ziehe ich folgendes raus (bezogen auf Punkt 2 Vererbung)

Wenn deine Klassen jeweils von der Basisklasse erbt - dann kannst du doch in jeder dieser Klassen über die geerbten Methoden Redefinitionen herstellen oder?
Und in der Redefinition würde zum Beispiel erst der eigentliche Code über super->xyz ausgeführt werden und dann deine Abwandlungen...

Aber wie gehabt geht das wohl völlig am Thema vorbei :D

Liebe Grüße trotzdem Enno :D :P

die Hausi

Re: Interface/ Klasse oder Vererbung?

Beitrag von ewx (Top Expert / 4848 / 312 / 642 ) »
Moin Hausi, ja, du hast Recht. Das geht.
Aber eben auch nur das. Eine Basisklasse ist eine Klasse, die alle generellen Attribute und Methoden eines Objektes besitzen sollte.
Die erbenden Klassen sind dann speziellere Objekte.

Ich möchte aber z.B. IS_MODIFIED nicht als Super- oder Basisklasse definieren weil
- es das erstens nicht ist
- keine Mehrfachvererbung möglich ist. Wenn ich also noch generelle Funktionen wie "Wechsel von EDIT auf DISPLAY und umgekehrt", dann kann ich keine zusätzliche Vererbung machen.

Wobei ich grade erkenne, dass ich fast den gleichen Post schon mal gepostet habe...
http://www.abapforum.com/forum/viewtopi ... =3&t=20196

Dort beziehe ich mich auf Spiderman:
https://stefanhenneken.wordpress.com/20 ... nterfaces/

Da wird das Problem eigentlich ganz plastisch dargestellt.

Du hast eine Oberklasse "Organismus" und Unterklassen:
- Säugetiere
-- Hund
-- Mensch
- Insekten
-- Spinne

Mit entsprechenden Eigentschaften.

Und dann kommt Spiderman... ;D

Re: Interface/ Klasse oder Vererbung?

Beitrag von ewx (Top Expert / 4848 / 312 / 642 ) »
erp-bt hat geschrieben:Hi,

Es geht ja gar nicht so sehr um den Decorator, sondern um die Möglichkeit Interfaces abstrakt in einer abstrakten Klasse zu definieren, die dann in der jeweiligen konkreten Implementierung ausprogrammiert werden, aber gleichzeitig Attribute und Methoden der abstrakten Klasse zu nutzen, damit man eben nicht alles konkret in der "Kind"-Klasse implementieren muss. Das "Decoratee"-Attribut ist ja immer eine konkrete Instanz. Und natürlich können auch mehrere Attribute existieren.
Kannst du dir noch mal die Mühe machen und ein konkretes Beispiel liefern, bitte?
Ich habe keine Ahnung, wie ich die Kombi sinnvoll nutzen kann... :(
Das wäre total super! :wink:

Re: Interface/ Klasse oder Vererbung?

Beitrag von gtoXX (Specialist / 213 / 44 / 36 ) »
ewx hat geschrieben:Hallo zusammen!

Ich stehe mal wieder auf dem OO-Schlauch...

Ich habe mehrere Objekte die alle die gleiche Funktionalität bekommen sollen: IS_MODIFIED?
Dafür brauche ich die Methoden SET_MODIFIED und IS_MODIFIED sowie mindestens ein Attribut.

Variante 1: Interface
Ich definiere ein Interface und definiere die Methoden. Das Interface binde ich dann in die benötigten Klassen ein. Allerdings muss ich die Implementierung dann in jeder Klasse vornehmen. Das möchte ich nicht.

Variante 2: Vererbung
Ich definiere eine Basisklasse mit den beiden Methoden und lasse die Objekt-Klassen von dieser Klasse erben. Dann muss ich die Implementierung nur einmal in der Basis-Klasse vornehmen. Das möchte ich aber auch nicht, weil "MODIFIED" ja keine Hauptklasse in dem Sinne ist. Wenn ich das einmal gemacht habe, dann kann ich keine weiteren Funktionen nach diesem Muster einbauen.

Variante 3: (Interface ->) Attribut -> Klasse
Ich definiere eine Klasse mit den beiden Methoden und dem Kennzeichen "modified". Diese Klasse binde ich entweder direkt in meine Objekt-Klassen ein.
Nachteile:
- Das modified-Objekt muss instanziiert werden. Nicht schlimm aber auch nicht schön.
- Der Zugriff erfolgt immer über Attribut->Methode. Die Methode gehört also irgendwie nicht wirklich zu der Objektklasse...

Variante 4: Modified-Controller
Ich erstelle einen Controller in dem ich mir mittels ZCL_HELPER_MODIF=>SET_MODIFIED( Objekt-Klasse ) merke, welche Objekte geändert wurden.
Mit IS_MODIFIED( Objekt-Klasse ) bekäme ich einfach wieder raus, ob das Objekt geändert wurde.
oder es erfolgt ein RAISE EVENT i_am_modified( me ).

Herausforderung:
Ich habe ein Hauptobjekt mit Unterobjekten:
Hauptobjekt z.B. LIEFERBELEG
Unterobjekte z-B.
- Texte
- Packstücke

Wenn "Texte" geändert wurden, dann meldet das Texte-Objekte, dass es geändert wurde.
Lieferbeleg-Objekt muss natürlich seine Objekte nach Änderungen abfragen, das ist klar.

Es sollte also eine einheitliche Schnittstelle nach Außen geben (Interface) mit der Möglichkeit, die Funktionalität selbst in einem eigenen Objekt zu haben.
Das ganze sollte zudem nur lose an das Objekt gekoppelt sein. Ich möchte gegebenenfalls noch andere generische Funktionalitäten anbinden, wie z.B. "HASH-Wert des Objektes ermitteln", "Bearbeitung auf 'Anzeige' setzen" oder ähnliches.

Hat jemand eine gute Idee/ Entwurfsmuster dafür?

Gruß und schönes WE!

Der Post ist zwar schon etwas älter, aber trotzdem eine Antwort. Im Endeffekt willst Du eine Art Observer Pattern. Ein Unterobjekt soll sein Oberobjekt über eine Änderung informieren. Attribute sind hier gar nicht zwingend nötig.

Definiere ein Interface, das ein Ereignis hat. Dieses Ereignis wird in deinem Unterobjekt geraised zb. Beim Set_Value. Dein Oberobjekt, registriert einen Handler auf das in ihm ja enthalte Unterobjekt und weiß dann im Handler was es damit zu tun hat. Ggfs. kannst Du im Ereignis ein Attribut einer abstrakten Oberklasse oder ein Inteface einbauen und beim Raisen im Unterobjekt das Objekt selbst mitgeben. So steht Dir im Oberobjekt frei, was Du damit machst. Es besteht auch keine Abhängigkeit von einer Hierarchie. Dein Oberobjekt kann vom Typ A sein, während das Unterobjekt vom Typ C ist, der nichts von A weiß. Auf diese Art werden klassisch MVC / MVVM Pattern umgesetzt.

Sind deine Unterobjekte selbst wiederrum zusammengesetzte Objekte, wird dafür gesorgt, das in den davon erbenden Klassen immer das Attribut der Oberklasse gesetzt wird. So hält in einer Hierarchie ( zb. Fenster mit Textbox ) nur eine Klasse letztlich den State. Für die Verwender des zusammengesetzen objekte ist in der Regel ja nicht interessant welches Unterelement genau sich geändert hat, sondern nur das eine Änderung vorliegt auf die Reagiert werden muss im "Controller".

Folgende Benutzer bedankten sich beim Autor gtoXX für den Beitrag (Insgesamt 2):
ralf.wenzelewx

"Code lügt nicht ^^"

Re: Interface/ Klasse oder Vererbung?

Beitrag von ralf.wenzel (Top Expert / 3924 / 200 / 280 ) »
Sehr gute Antwort. Wie alt die Frage ist, ist nicht von Belang, das ist ja hier auch ein Nachschlagewerk.



Ralf

Folgende Benutzer bedankten sich beim Autor ralf.wenzel für den Beitrag:
gtoXX

Bild
Ralf Wenzel Heuristika SAP-Development
25 Jahre SAP-Entwickler • 20 Jahre Freiberufler
PublikationenUngarische NotationXing

Re: Interface/ Klasse oder Vererbung?

Beitrag von ewx (Top Expert / 4848 / 312 / 642 ) »
gtoXX hat geschrieben:Im Endeffekt willst Du eine Art Observer Pattern.
So hatte ich das noch gar nicht gesehen...
Danke für den Input. Das probiere ich mal aus!

Seite 1 von 1

Vergleichbare Themen

4
Antw.
3706
Views
Java Definition Interface/Abstrakte Klasse
von erp-bt » 19.03.2019 14:01 • Verfasst in Java & SAP®
5
Antw.
3575
Views
Klasse soll Typdefinition von anderer Klasse nutzen
von debianfan » 24.05.2017 11:30 • Verfasst in ABAP Objects®
1
Antw.
2483
Views
Lokale Klasse autom. in globale Klasse ändern
von JohnLocklay » 09.01.2019 09:10 • Verfasst in ABAP Objects®
7
Antw.
4474
Views
Interfaces vs. Vererbung
von ewx » 02.12.2014 18:32 • Verfasst in ABAP Objects®
0
Antw.
1374
Views
Vererbung von CL_RSR_WWW_MODIFY_TABLE
von ratoshuan » 04.04.2006 18:45 • Verfasst in Web-Dynpro, BSP + BHTML

Aktuelle Forenbeiträge

Dialog-Container mit Toolbar/Status
vor 18 Stunden von black_adept gelöst 23 / 3838
User Exit EXIT_RQCPRM10_001
vor 19 Stunden von a-dead-trousers 2 / 329
Trennen Strasse und Hausnummer
Gestern von payten 13 / 10699
Daten an Tabelle binden
Gestern von Lukas Sanders 2 / 1381

Newsletter Anmeldung

Keine Beiträge verpassen! Wöchentlich versenden wir lesenwerte Beiträge aus unserer Community.
Die letzte Ausgabe findest du hier.
Details zum Versandverfahren und zu Ihren Widerrufsmöglichkeiten findest du in unserer Datenschutzerklärung.

Aktuelle Forenbeiträge

Dialog-Container mit Toolbar/Status
vor 18 Stunden von black_adept gelöst 23 / 3838
User Exit EXIT_RQCPRM10_001
vor 19 Stunden von a-dead-trousers 2 / 329
Trennen Strasse und Hausnummer
Gestern von payten 13 / 10699
Daten an Tabelle binden
Gestern von Lukas Sanders 2 / 1381

Unbeantwortete Forenbeiträge

aRFC im OO-Kontext
vor 4 Wochen von ralf.wenzel 1 / 2912
Hilfe bei SWEC/SWE2
September 2024 von retsch 1 / 9506