Monday, September 24, 2007

Patterns 1 - Gang of Four

Seit ich mich mit Entwurfsmuster, oder eben Patterns wie ich normalerweise sage, beschäftige haben sich einzelne Steine zu einem grösseren Mosaik zusammengefunden. Das Mosaik hat noch viele Lücken, aber ich möche hier alle mir wichtig erscheinenden und von mir verstandenen Patterns zusammenfassen. Dies ist mein aktuelles "Weltbild" des objektorientierten Software-Designs. Noch ein Wort zu meiner Welt. Meine Welt ist die der grösseren datenzentrierten Geschäftsanwendungen, mit einer Rich-Client Benutzeroberfläche.

In der Folge möchte ich in mehreren Beiträge diese Patterns auflisten und zusammenstellen. In einem ersten Beitrag gehts es um die 'Gang of Four - Patterns' welche eine Ansammlung von systemnahen, technisch orientierten Patterns darstellen.

Abstract Factory: Erzeugt eine Familie von Objekte unterschiedlicher Typen ohne dass man bei der Benutzung gegen eine konkrete Familie programmiert. Als Beispiel dient hier eine IDbFactory welche IConnection, ITransaction für den Datenbankzugriff erstellt. IDbFactory kann nun konkrete für SQL-Server oder Oracle implementiert werden ohne dass es für den Benutzer von IDbFactory einen Unterschied ausmacht.

Builder: Abstrahiert den Konstruktionsprozess für komplexe Objekte. Falls erforderlich kann der Konstruktionsprozess für andere Typen wiederverwendet werden. So kann zum Beispiel das abstrakte Erstellen einer Rechnung mit einer Anzahl Rechnungspositionen mit einem abstrakten Builder realisiert werden. Als Varianten für konkrete Builder wäre ein KreditorenrechnungsBuilder und ein DebitorenrechnungsBuilder möglich

Factory Method: Erzeugt ein Objekt wobei die implementierende Subclass über den konkreten Typ des erzeugten Objekts entscheidet. Ist mit dem Abstract Factory-Pattern dadurch verwandt, dass dort eine Familie von Objekten und hier nur ein Objekt erzeugt wird.

Singleton: Stellt sicher, dass eine Klasse nur einmal instanziert ist und global zugegriffen werden kann. Damit kann zum Beispiel eine Infastrukturdienst wie die Protokollierung einfach für alle Programmstellen zugreiffbar gemacht werden. Das Pattern sollte aber sehr bedacht eingesetzt werden, da man sich damit sehr einfache versteckte Abhängigkeiten baut, welche die Flexibiltät und Wartbarkeit von Programmcode stark einschränken.

Adapter: Ermöglicht den Zugriff auf eine Klasse via ein Interface welches die Klasse selbst aber nicht unterstützt. Als Beispiel könnte man damit in einer Windows.Forms-Anwendung Controls über eine Interface IControl ansprechen obwohl die Windows.Forms-Library kein solches Interface unterstützt. Ein ControlAdapter würde dann Control auf IControl adaptieren.

Composite: Ist eine Datenstruktur in Form eines Baumes mit Vater-Kind-Beziehungen. Jeder Knoten im Baum ist wieder ein Composite mit weiteren enthaltenen Composites oder dann ein Leaf (Blatt) ohne weiteren Composites.

Decorater: Damit kann zur Laufzeit ein Objekt dynamisch erweitert werden. Bestehende Methoden können erweitert werden und auf dem Decorater können neue Funktionalitäten für das Objekt realisiert werden. Als Beispiel könnte man damit eine Klasse Strassenverbindung abhängig von der Strassensituation als GesperrteStrasse oder als StrasseMitStau instanzieren was dann das Verhalten der Strassenverbindung zur Laufzeit beeinflusst.

Chain of responsibilty: Ermöglicht dass eine Anforderung oder eine Meldung von einer Anzahl Objekten verarbeitet werden kann, wobei jedes Objekt eine spezifische Aufgabe wahrnimmt und die Meldung an ein nächstes weiterleitet. Als Beispiel kann das Verarbeiten einer Meldung in verschiedenen Schritten angesehen werden: 'Dekomprimieren der Meldung' -> 'Authentizität der Meldung prüfen' -> 'Meldung interpretieren' usw....

Command: Bildet eine Anfrage an ein Objekt ab und erlaubt damit Transport, Protokollierung, Persistierung usw. der Anfrage. Zum Beispiel kann damit ein Command in einer Queue gespeichert und zu einem späteren Zeitpunkt ausgeführt werden.

State: Ermöglicht einem Objekt sein Verhalten abhängig von einem Zustand zu ändern. Die Implementation des Verhalten wird an den State delegiert.

Strategy: Kapselt einen Algorithmus in einer Klasse und ermöglicht damit eine allgemeine Verarbeitung mit spezifischen Strategien zu parametriesieren. So könnte damit die Berechnung einer Strassenverbindung mit der 'KuerzesterWegStrategie' oder mit der 'SchnellsterWegStrategie' parametrisiert werden. Der darunterliegende Berechnungsalgorithmus ist somit unabhängig und kann mit verschiedenen Strategien kombiniert werden.

Template Method: Kapselt Teile eines Algorithmus in Methoden und erlaubt Subklassen diese Teile zu implementieren. Somit realisiert eine Basisklasse das Grundgerüst eines Algorithmus und die Subklassen können einzelne Verarbeitungsschritte verfeinern.

No comments: