|
In Java ist es möglich, abstrakte Methoden zu definieren. Im Gegensatz zu konkreten Methoden enthalten sie nur die Deklaration des Methodenkopfes, aber keine Implementierung des Methodenrumpfes. Syntaktisch unterscheiden sich abstrakte Methoden dadurch, daß anstelle der geschweiften Klammern mit den auszuführenden Anweisungen lediglich ein Semikolon steht. Zusätzlich wird die Definition mit dem Attribut abstract versehen.
Abstrakte Methoden können nicht aufgerufen werden. So definieren sie nur eine Schnittstelle, die durch Überlagerung in einer abgeleiteten Klasse implementiert werden kann.
Eine Klasse, die mindestens eine abstrakte Methode enthält, wird selbst als abstrakt angesehen und muß ebenfalls mit dem Schlüsselwort abstract versehen werden. Abstrakte Klassen können nicht instanziert werden, da sie Methoden enthalten, die nicht implementiert wurden. Statt dessen werden abstrakte Klassen abgeleitet, und in der abgeleiteten Klasse werden eine oder mehrere der abstrakten Methoden implementiert. Eine abstrakte Klasse wird konkret, wenn alle ihre Methoden implementiert sind. Die Konkretisierung kann dabei auch schrittweise über mehrere Vererbungsstufen erfolgen. |
![]() |
|
![]() |
Wir wollen uns ein Beispiel ansehen, um diese Ausführungen zu verdeutlichen. Zum Aufbau einer Mitarbeiterdatenbank soll zunächst eine Basisklasse definiert werden, die jene Eigenschaften implementiert, die für alle Mitarbeiter zutreffen, wie beispielsweise persönliche Daten oder der Eintrittstermin in das Unternehmen. Gleichzeitig soll diese Klasse als Basis für spezialisierte Unterklassen verwendet werden, um die Besonderheiten spezieller Mitarbeitertypen, wie Arbeiter, Angestellte oder Manager, abzubilden. Da die Berechnung des monatlichen Gehalts zwar für jeden Mitarbeiter erforderlich, in ihrer konkreten Realisierung aber abhängig vom Typ des Mitarbeiters ist, soll eine abstrakte Methode monatsBrutto in der Basisklasse definiert werden, die in den abgeleiteten Klassen konkretisiert wird. |
![]() |
|
![]() |
Das folgende Beispiel zeigt die Implementierung der Klassen Mitarbeiter, Arbeiter, Angestellter und Manager zur Realisierung der verschiedenen Mitarbeitertypen. Zusätzlich wird die Klasse Gehaltsberechnung definiert, um das Hauptprogramm zur Verfügung zu stellen, in dem die Gehaltsberechnung durchgeführt wird. Dazu wird ein Array ma mit konkreten Untertypen der Klasse Mitarbeiter gefüllt (hier nur angedeutet) und dann für alle Elemente das Monatsgehalt durch Aufruf von monatsBrutto ermittelt.
001 /* Gehaltsberechnung.java */ 002 003 import java.util.Date; 004 005 abstract class Mitarbeiter 006 { 007 int persnr; 008 String name; 009 Date eintritt; 010 011 public Mitarbeiter() 012 { 013 } 014 015 public abstract double monatsBrutto(); 016 } 017 018 class Arbeiter 019 extends Mitarbeiter 020 { 021 double stundenlohn; 022 double anzahlstunden; 023 double ueberstundenzuschlag; 024 double anzahlueberstunden; 025 double schichtzulage; 026 027 public double monatsBrutto() 028 { 029 return stundenlohn*anzahlstunden+ 030 ueberstundenzuschlag*anzahlueberstunden+ 031 schichtzulage; 032 } 033 } 034 035 class Angestellter 036 extends Mitarbeiter 037 { 038 double grundgehalt; 039 double ortszuschlag; 040 double zulage; 041 042 public double monatsBrutto() 043 { 044 return grundgehalt+ 045 ortszuschlag+ 046 zulage; 047 } 048 } 049 050 class Manager 051 extends Mitarbeiter 052 { 053 double fixgehalt; 054 double provision1; 055 double provision2; 056 double umsatz1; 057 double umsatz2; 058 059 public double monatsBrutto() 060 { 061 return fixgehalt+ 062 umsatz1*provision1/100+ 063 umsatz2*provision2/100; 064 } 065 } 066 067 public class Gehaltsberechnung 068 { 069 private static final int ANZ_MA = 100; 070 private static Mitarbeiter ma[]; 071 private static double bruttosumme; 072 073 public static void main(String args[]) 074 { 075 ma = new Mitarbeiter[ANZ_MA]; 076 077 //Mitarbeiter-Array füllen, z.B. 078 //ma[0] = new Manager(); 079 //ma[1] = new Arbeiter(); 080 //ma[2] = new Angestellter(); 081 //... 082 083 //Bruttosumme berechnen 084 bruttosumme = 0.0; 085 for (int i=0; i<ma.length; ++i) { 086 bruttosumme += ma[i].monatsBrutto(); 087 } 088 System.out.println("Bruttosumme = "+bruttosumme); 089 } 090 } |
Gehaltsberechnung.java |
Unabhängig davon, ob in einem Array-Element ein Arbeiter, Angestellter oder Manager gespeichert wird, führt der Aufruf von monatsBrutto dank der dynamischen Methodensuche die zum Typ des konkreten Objekts passende Berechnung aus. Auch weitere Verfeinerungen der Klassenhierarchie durch Ableiten neuer Klassen erfordern keine Veränderung in der Routine zur Berechnung der monatlichen Bruttosumme.
So könnte beispielsweise eine neue Klasse GFManager (ein Manager, der Mitglied der Geschäftsführung ist) aus Manager abgeleitet und problemlos in die Gehaltsberechnung integriert werden:
001 public class GFManager 002 extends Manager 003 { 004 double gfzulage; 005 006 public double monatsBrutto() 007 { 008 return super.monatsBrutto()+gfzulage; 009 } 010 } |
In der abgedruckten Form ist das Programm in Listing 7.26 natürlich nicht lauffähig, denn das Array ma wird nicht vollständig initialisiert. Ansonsten ist es aber korrekt und illustriert beispielhaft die Anwendung abstrakter Klassen und Methoden. |
![]() |
|
![]() |
|
Go To Java 2, Addison Wesley, Version 1.0.2, © 1999 Guido Krüger, http://www.gkrueger.com |