Flexibel programmieren mit dem Fluent Interface

Seite 5: Rettender Erbauer

Inhaltsverzeichnis

Die Rettung naht in Form des Erzeugungsmusters "Erbauer" (Builder). Ein Erbauer trennt die Repräsentation eines Objekts von seiner Konstruktion, in diesem Falle die konstruierenden Methoden (und wofür sie stehen) vom Rest des Abschnitts. Ein Erbauer in Kombination mit einer flüssigen Schnittstelle, von Fowler "Expression Builder" [e] genannt, ist eine deutliche Bereicherung im Hinblick auf die Lesbarkeit:

Abschnitt abschnitt =
ErzeugeAbschnitt.mitNamen("abschnittsname").mitWert("a").anStelle(1).undMitWert
("b").anStelle(2).jetzt();

Zuerst fällt auf, dass der Erbauer selbst mit einem Verb statt mit einem Nomen benannt ist. Dieser Kniff [f] lässt nun einen vollständigen Satz im Imperativ entstehen:

"Erzeuge Abschnitt mit Namen abschnittsname mit Wert a an Stelle 1 und mit Wert b an Stelle 2, jetzt!"

Der erzeugte [code]Abschnitt[/code] beschränkt sich auf die Repräsentation und hat keine konstruierenden Methoden mehr (Abb. 3).

Zurück gibt der Flüssige Erbauer ein Objekt vom Typ Abschnitt, der keine konstruierenden Methoden mehr hat und sich ganz um die Repräsentation seiner selbst kümmern kann. Abbildung 3 zeigt die API der Klassen ErzeugeAbschnitt und Abschnitt.

An dieser Stelle lässt sich einwenden, dass noch kein Separation of Concerns stattgefunden hat. Immerhin gibt es ja noch Methoden wie setName(String name) und put(int Stelle, String wert). Doch hier ist zu unterscheiden zwischen konstruierenden und verändernden Methoden. Alle konstruierenden sind jetzt am Builder verankert. Ob das Objekt nach der Konstruktion noch veränderbar sein darf, ist eine Designentscheidung, die unabhängig von der Konstruktion ist. In diesem Fall ist die Entscheidung für ein veränderliches Objekt gefallen; unveränderliche Objekte hätten keine solchen modifizierenden Methoden.

Eine Besonderheit stellt die Methode jetzt() an der Erbauer-Klasse ErzeugeAbschnitt dar. Prinzipiell könnte man einem Abschnitt beliebig viele Werte hinzufügen. Hierzu muss stets der Erbauer herhalten, und so gibt jede Methode, die einen Wert für eine Stelle aufnimmt, letztendlich ein Objekt vom Typ ErzeugeAbschnitt zurück. Will man jedoch keinen Wert mehr hinzufügen, soll der Rückgabewert ein Abschnitt sein. Dies erreicht der Aufruf von jetzt(), der den Verantwortungsbereich des flüssigen Erbauers terminiert. Von hier an ist der Abschnitt auf sich allein gestellt. Ein lauffähiges Beispiel steht auf dem iX-Listingserver bereit.