Ich verstehe das "Brücken" -Designmuster überhaupt nicht. Ich habe verschiedene Websites durchgesehen, aber sie haben nicht geholfen.
Kann mir jemand helfen, das zu verstehen?
Ich verstehe das "Brücken" -Designmuster überhaupt nicht. Ich habe verschiedene Websites durchgesehen, aber sie haben nicht geholfen.
Kann mir jemand helfen, das zu verstehen?
Antworten:
In OOP verwenden wir Polymorphismus, sodass eine Abstraktion mehrere Implementierungen haben kann. Schauen wir uns das folgende Beispiel an:
Eine neue Anforderung wurde eingeführt und muss die Beschleunigungsperspektive der Züge berücksichtigen. Ändern Sie daher den Code wie folgt.
Der obige Code ist nicht wartbar und nicht wiederverwendbar (vorausgesetzt, wir könnten den Beschleunigungsmechanismus für dieselbe Gleisplattform wiederverwenden). Der folgende Code wendet das Brückenmuster an und trennt die beiden unterschiedlichen Abstraktionen Zugtransport und Beschleunigung .
quelle
Monorail
da es nicht wirklich zwei Wörter ist, es ist ein einzelnes (zusammengesetztes) Wort. Eine MonoRail wäre eine Unterklasse von Rail anstelle einer anderen Art von Rail (die es ist). Genau wie wirSunShine
oder nicht verwenden würdenCupCake
, würden sieSunshine
und seinCupcake
Während die meisten Entwurfsmuster hilfreiche Namen haben, finde ich den Namen "Bridge" in Bezug auf das, was er tut, nicht intuitiv.
Konzeptionell übertragen Sie die von einer Klassenhierarchie verwendeten Implementierungsdetails in ein anderes Objekt, normalerweise mit einer eigenen Hierarchie. Auf diese Weise entfernen Sie eine enge Abhängigkeit von diesen Implementierungsdetails und ermöglichen, dass sich die Details dieser Implementierung ändern.
Im Kleinen vergleiche ich dies mit der Verwendung eines Strategiemusters, mit dem Sie ein neues Verhalten einfügen können. Anstatt jedoch nur einen Algorithmus zu verpacken, wie dies häufig in einer Strategie zu sehen ist, ist das Implementierungsobjekt in der Regel mehr mit Features gefüllt. Und wenn Sie das Konzept auf eine gesamte Klassenhierarchie anwenden, wird das größere Muster zur Brücke. (Auch hier hasse den Namen).
Es ist kein Muster, das Sie jeden Tag verwenden werden, aber ich fand es hilfreich, wenn Sie eine potenzielle Explosion von Klassen verwalten, die auftreten kann, wenn Sie (offensichtlich) mehrere Vererbungen benötigen.
Hier ist ein reales Beispiel:
Ich habe ein RAD-Tool, mit dem Sie Steuerelemente auf einer Entwurfsoberfläche ablegen und konfigurieren können. Daher habe ich ein Objektmodell wie das folgende:
Und so weiter, mit vielleicht einem Dutzend Kontrollen.
Dann wird eine neue Anforderung hinzugefügt, um mehrere Themen zu unterstützen (Look-n-Feel). Lassen Sie uns sagen , dass wir die folgenden Themen haben:
Win32
,WinCE
,WinPPC
,WinMo50
,WinMo65
. Jedes Design hätte andere Werte oder Implementierungen für renderbezogene Operationen wie DefaultFont, DefaultBackColor, BorderWidth, DrawFrame, DrawScrollThumb usw.Ich könnte ein Objektmodell wie dieses erstellen:
usw. für einen Kontrolltyp
usw., für jeden anderen Kontrolltyp (wieder)
Sie bekommen die Idee - Sie bekommen eine Klassenexplosion der Anzahl der Widgets, mal der Anzahl der Themen. Dies erschwert den RAD-Designer, indem er ihn auf jedes Thema aufmerksam macht. Wenn Sie neue Designs hinzufügen, muss der RAD-Designer geändert werden. Darüber hinaus gibt es eine Menge gemeinsamer Implementierungen innerhalb eines Themas, deren Vererbung sich lohnen würde, aber die Steuerelemente erben bereits von einer gemeinsamen Basis (
Widget
).Stattdessen habe ich eine separate Objekthierarchie erstellt, die das Thema implementiert. Jedes Widget enthält einen Verweis auf das Objekt, das die Rendervorgänge implementiert. In vielen Texten wird diese Klasse mit einem angefügt,
Impl
aber ich habe von dieser Namenskonvention abgewichen.So
TextboxWidget
sieht mein jetzt so aus:Und ich kann meine verschiedenen Maler meine themenspezifische Basis erben lassen, was ich vorher nicht konnte:
Eines der schönen Dinge ist, dass ich die Implementierungen zur Laufzeit dynamisch laden kann, so dass ich so viele Themen hinzufügen kann, wie ich möchte, ohne die Kernsoftware zu ändern. Mit anderen Worten, meine "Implementierung kann unabhängig von der Abstraktion variieren".
quelle
Win32TextboxPainter
undWin32ListPainter
ausWin32WidgetPainter
. Sie können einen Vererbungsbaum auf der Implementierungsseite haben, aber es sollte mehr Generika (vielleicht seinStaticStyleControlPainter
,EditStyleControlPainter
undButtonStyleControlPainter
) mit allen benötigten Grundoperationen überschrieben je nach Bedarf. Dies ist näher an dem realen Code, auf den ich das Beispiel gestützt habe.Die Brücke beabsichtigt, eine Abstraktion von ihrer konkreten Implementierung zu entkoppeln , so dass beide unabhängig voneinander variieren können:
Die Brücke erreicht dies durch Komposition:
Zusätzliche Bemerkungen zu einer häufigen Verwirrung
Dieses Muster ist dem Adaptermuster sehr ähnlich: Die Abstraktion bietet eine andere Schnittstelle für eine Implementierung und verwendet dazu die Komposition. Aber:
In diesem ausgezeichneten wegweisenden Buch über Entwurfsmuster stellen die Autoren außerdem fest, dass:
quelle