Decorator Pattern
Analyse- und Design-Pattern
CAS SWE FS14
Roland Müller
Samuel Schärer
Entwurfsmuster der «Gang of Four»
◦ Strukturmuster fassen Klassen und Objekte zu
grösseren Strukturen zusammen
Adapter
Bridge
Decorator
Facade
Composite
…
Klassifikation
2
Kaffee-Sorten
◦ Arabica
◦ Koffeinfrei
Kaffee-Zusätze
◦ Zucker
◦ Milch
Beispiel Kaffeebar
3
Varianten
4
2 zusätzliche Kaffee-Sorten:
Erweiterungen
5
2 zusätzliche Kaffee-Zusätze:
Erweiterungen
6
Erweiterungen sind Aufwändig und
Fehleranfällig
◦ Pro neuer Zusatz müssen 4 neue Klassen erstellt werden
◦ Wenn sich der Preis einer Sorte ändert müssen alle Klassen mit
dieser Sorte angepasst werden
Keine Flexibilität
◦ Es sind nur die fix modellierten Kombinationen möglich
Mangelnde Dynamik
◦ Keine Möglichkeit während der Laufzeit dynamisch
Zusätze hinzuzufügen oder zu entfernen
Nachteile
7
Die Funktionalität von Objekten
dynamisch erweitern, ohne dabei
deren Klasse zu verändern
Decotator-Zweck
8
Die Kaffee-Sorten sowie die Kaffee-Zusätze bleiben
konstant
Kaffee-Sorten
Kaffee-Zusätze
Variabel sind die Kombinationen aus Kaffee-Sorte und den
verschiedenen Zusätzen
Decorator-Prinzip
9
Eine Kaffee-Sorte mit beliebigen Zusätzen
umhüllen (dekorieren)
Arabica
Milch
Zucker
Decorator-Idee
10
Aufgaben von innen nach aussen erledigen
Arabica
getPreis()
getPreis()
getPreis()
3.0
Milch
+0.5
+0.5
+0.1
3.60
Zucker
Decorator-Idee
11
Konkrete Sorten
Konkrete Zusätze
Modell
(Beispiel Kaffee)
12
Konkrete Sorten
public interface Kaffee {
public double getPreis();
public void druckeBeschreibung();
}
Konkrete Zusätze
Implementierung
13
Konkrete Sorten
public class Arabica implements Kaffee {
public void druckeBeschreibung() {
System.out.print("Arabica");
}
public double getPreis() {
return 3.00;
}
}
Konkrete
Konkrete
Zusätze
Zusätze
Implementierung
14
Konkrete Sorten
public abstract class Zusatz implements Kaffee {
protected Kaffee kaffee;
public Zusatz(Kaffee kaffee) {
this.kaffee = kaffee;
}
}
Konkrete
Konkrete
Zusätze
Zusätze
Implementierung
15
public class Milch extends Zusatz {
public Milch(Kaffee kaffee) {
Konkrete Sorten
super(kaffee);
}
public void druckeBeschreibung() {
kaffee.druckeBeschreibung();
System.out.print(", Milch");
}
public double getPreis() {
return kaffee.getPreis() + 0.50;
}
}
Konkrete
Konkrete
Zusätze
Zusätze
Implementierung
16
public class Zucker extends Zusatz {
public Zucker(Kaffee kaffee) {
Konkrete Sorten
super(kaffee);
}
public void druckeBeschreibung() {
kaffee.druckeBeschreibung();
System.out.print(", Zucker");
}
public double getPreis() {
return kaffee.getPreis() + 0.10;
}
}
Konkrete
Konkrete
Zusätze
Zusätze
Implementierung
17
public class Kaffeebar {
public static void main(String[] args) {
Kaffee meinKaffee = new Zucker(new Milch(new Arabica()));
meinKaffee.druckeBeschreibung();
// Arabica, Milch, Zucker
System.out.println("Preis: CHF "+ meinKaffee.getPreis());
// Preis: CHF 3.60
}
}
Verwendung
Arabica
Milch
Zucker
18
Modell
(Allgemein)
19
Wenn bereits Code existiert, den man mit geringem
Aufwand so anpassen möchte, dass später Klassen
einfach erweitert werden können
Wenn man verhindern will, dass durch allfällige
Erweiterungen zu viele Subklassen entstehen
Wenn man zur Laufzeit Status oder Verhalten einer
Klasse erweitern und beliebig kombinieren will
Wenn man Klassen erweitern oder hinzufügen will
ohne dass andere Klassen davon betroffen sind
(Open/Closed Prinzip)
Wann sollte das Decorator Pattern
in Erwägung gezogen werden?
Wenn ein dynamisches Erweitern einer Komponente
nicht erforderlich ist, sind ev. Subklassen besser
geeignet
Höhere Komplexität als mit Subklassen
Die oft langen Aufrufketten erschweren das Finden
von Fehlern und führen zu unübersichtlichem
Initialisierungscode
Objekt-Vergleiche können Fehler verursachen
Dekorierte Komponenten sind als Objekt nicht
identisch
Was spricht gegen das Decorator
Pattern?
21
Adapter/Wrapper
◦ Wenn ein Interface zwischen zwei Klassen
(ohne zusätzliche Funktionalität) ausreicht
Composite
◦ Wenn es darum geht eine Hierarchie abzubilden
(wie z.B. Filesystem)
Proxy
◦ Wenn es darum geht Zugriffsberechtigungen auf
Objekte zu steuern
Strategy
◦ Wenn das Original Objekt geändert werden soll anstatt
nur Zugriff zu gewähren
Wann sollten verwandte Pattern in
Betracht gezogen werden?
Java Swing JScrollPane
Anwendungsbeispiele
Java IO
Anwendungsbeispiele
Fragen?
25