Als ich anfing, Java zu lernen, verwendeten die Lehrer, wenn sie über Vererbung sprachen, immer gern ein Beispiel zur Erklärung, und zwar das Zeichnen. Hier haben wir einen Pinsel, der Quadrate, Rechtecke und Kreise zeichnen kann (jeder weiß, wie das geht, daher erkläre ich es nicht). Aber jetzt müssen wir diese Formen einfärben, und es gibt drei Farben: Weiß, Grau und Schwarz. Hier können wir 3*3=9 Formen zeichnen: weiße Quadrate, weiße Rechtecke, weiße Kreise... An diesem Punkt wissen wir schon fast, dass es zwei Lösungen gibt:

  • Lösung 1: Für jede Form verschiedene Farbversionen bereitstellen.
  • Lösung 2: Farben und Formen nach tatsächlichem Bedarf kombinieren.

Wenn wir Lösung 1 zur Implementierung verwenden, können wir es auch so verstehen? Für jede Farbe verschiedene Formversionen bereitstellen? Das ist völlig möglich. Wie folgt:

Anhand der beiden Formen in Lösung 1 verstehen wir alle dieses Problem deutlich: Wenn wir eine Ellipse hinzufügen, müssen wir dann drei weitere Farben hinzufügen? Wenn wir eine grüne Farbe hinzufügen, müssen wir vier weitere Formen hinzufügen. Weiter hinzufügen. Weiter hinzufügen... Jede Hinzufügung erhöht die Anzahl der Klassen (wenn eine Farbe hinzugefügt wird, werden so viele Klassen hinzugefügt, wie es Formen gibt; wenn eine Form hinzugefügt wird, werden so viele Klassen hinzugefügt, wie es Farben gibt). Ich denke, kein Programmierer möchte das! Schauen wir uns also Lösung 2 an. Die von Lösung 2 bereitgestellte Lösung ist: zwei Elternklassen bereitstellen, eine für Farbe und eine für Form. Sowohl die Farb-Elternklasse als auch die Form-Elternklasse enthalten entsprechende Unterklassen, und dann werden Farben und Formen nach Bedarf kombiniert.

Für Situationen mit mehreren sich ändernden Dimensionen verwenden wir im Allgemeinen Lösung 2 zur Implementierung. Zusätzlich zur Verringerung der Anzahl der Klassen im System erleichtert sie auch die Systemerweiterung. Die Anwendung von Lösung 2 wird Bridge-Muster genannt.

1. Musterdefinition

Das Bridge-Muster trennt die Abstraktion von ihrer Implementierung, sodass sich beide unabhängig ändern können.

Das Bridge-Muster wandelt Vererbungsbeziehungen in Assoziationsbeziehungen um. Es reduziert die Kopplung zwischen Klassen, verringert die Anzahl der Klassen im System und reduziert die Codemenge.

Der Satz "die Abstraktion von ihrer Implementierung zu trennen" ist nicht leicht zu verstehen. Tatsächlich geht es dabei nicht darum, eine abstrakte Klasse von ihren abgeleiteten Klassen zu trennen, sondern darum, dass die abstrakte Klasse und ihre abgeleiteten Klassen ihre eigenen Objekte zur Implementierung verwenden. Wenn Sie es immer noch nicht verstehen können, wollen wir zunächst verstehen, was Abstraktion, Implementierung und Entkopplung sind.

Abstraktion:Ihr Konzept ist die Handlung oder der Prozess, aus einem komplexen Objekt eine oder mehrere Eigenschaften zu extrahieren und dabei nur auf andere Eigenschaften zu achten. In der objektorientierten Programmierung ist es der Prozess, die gemeinsamen Eigenschaften von Objekten zu extrahieren, um eine Klasse zu bilden.

Implementierung:Die konkrete Implementierung, die für die Abstraktion angegeben wird. Sie ist ein umgekehrter Prozess zur Abstraktion; Implementierung ist eine weitere Konkretisierung abstrakter Dinge.

Entkopplung:Entkopplung bedeutet, die Kopplung zwischen Abstraktion und Implementierung zu lösen oder die starke Beziehung zwischen ihnen in eine schwache Beziehung umzuwandeln und die Vererbungsbeziehung zwischen den beiden Rollen in eine Assoziationsbeziehung zu ändern.

Was jenen Satz betrifft: "die Abstraktion von ihrer Implementierung zu trennen", so bedeutet seine Anwendung in *Big Talk Design Patterns*, dass das Implementierungssystem mehrere Klassifizierungswinkel haben kann und sich jeder Winkel ändern kann. Dann trennt man diese Klassifizierungen aus mehreren Blickwinkeln, damit sie sich unabhängig ändern und die Kopplung zwischen ihnen verringert wird.

Die sogenannte Entkopplung im Bridge-Muster bedeutet, in einem Softwaresystem zwischen Abstraktion und Implementierung eine Assoziationsbeziehung (Kompositions- oder Aggregationsbeziehung) anstelle einer Vererbungsbeziehung zu verwenden, sodass sich beide relativ unabhängig ändern können. Das ist die Absicht des Bridge-Musters.

2. Musterstruktur

     

Die folgende Abbildung ist das UML-Strukturdiagramm des Brückenmusters:

Das Brückenmuster umfasst hauptsächlich die folgenden Rollen:

  • Abstraction: Abstrakte Klasse.
  • RefinedAbstraction: Verfeinerte Abstraktion.
  • Implementor: Implementor-Schnittstelle.
  • ConcreteImplementor: Konkreter Implementierer.

3. Musterimplementierung

Für das Musterszenario verwenden wir das Zeichnungsbeispiel. Sein UML-Strukturdiagramm sieht wie folgt aus:

Zuerst die Shape-Klasse: Diese Klasse ist eine abstrakte Klasse, die hauptsächlich eine Methode zum Zeichnen von Formen bereitstellt. Shape.java:

Beispiel

public abstract class Shape { Color color; public void setColor(Color color) { this.color = color; } public abstract void draw(); }

Dann die drei Formen.

Circle (Circle.java):

Beispiel

public class Circle extends Shape{ public void draw() { color.bepaint("Square"); } }

Rectangle (Rectangle.java):

Beispiel

public class Rectangle extends Shape{ public void draw() { color.bepaint("Rectangle"); } }

Square (Square.java):

Beispiel

public class Square extends Shape{ public void draw() { color.bepaint("Square"); } }

Color-Interface (Color.java):

Beispiel

public interface Color { public void bepaint(String shape); }

White (White.java):

Beispiel

public class White implements Color{ public void bepaint(String shape) { System.out.println("White" + shape); } }

Gray (Gray.java):

Beispiel

public class Gray implements Color{ public void bepaint(String shape) { System.out.println("Gray" + shape); } }

Black (Black.java):

Beispiel

public class Black implements Color{ public void bepaint(String shape) { System.out.println("Black" + shape); } }

Client (Client.java):

Beispiel

public class Client { public static void main(String[] args) { //White Color white = new White(); //Square Shape square = new Square(); //White square square.setColor(white); square.draw(); //Rectangle Shape rectange = new Rectangle(); rectange.setColor(white); rectange.draw(); } }

Ausgabe:

white square
white rectangle

4. Vor- und Nachteile des Musters

Vorteile

  • 1. Trennen Sie die abstrakte Schnittstelle und ihre Implementierung. Dies bietet eine bessere Lösung als Vererbung.
  • 2. Das Bridge-Muster verbessert die Erweiterbarkeit des Systems. Die Erweiterung einer der beiden sich ändernden Dimensionen erfordert keine Änderung des ursprünglichen Systems.
  • 3. Implementierungsdetails sind für Clients transparent, und Implementierungsdetails können vor Benutzern verborgen werden.

Nachteile

    
  • 1. Die Einführung des Bridge-Musters erhöht die Schwierigkeit, das System zu verstehen und zu entwerfen. Da die Aggregations-/Assoziationsbeziehung auf der Abstraktionsebene festgelegt wird, müssen Entwickler für Abstraktionen entwerfen und programmieren.
  • 2. Das Bridge-Muster erfordert, zwei unabhängig veränderliche Dimensionen im System korrekt zu identifizieren, daher hat sein Anwendungsbereich gewisse Einschränkungen.

5. Anwendungsszenarien

    
  • 1. Wenn ein System mehr Flexibilität zwischen der Abstraktionsrolle und der Implementierungsrolle seiner Komponenten hinzufügen muss und vermeiden will, eine statische Vererbungsverbindung zwischen den beiden Ebenen herzustellen, kann das Bridge-Muster eine Assoziationsbeziehung zwischen ihnen auf der Abstraktionsebene herstellen.
  • 2. Das Bridge-Muster eignet sich besonders für Systeme, die keine Vererbung verwenden möchten oder bei denen mehrstufige Vererbung zu einem sprunghaften Anstieg der Anzahl von Klassen führt.
  • 3. Eine Klasse hat zwei unabhängig voneinander veränderliche Dimensionen, und beide Dimensionen müssen erweitert werden.

6. Musterzusammenfassung

   
  • 1. Das Bridge-Muster bewirkt die Entkopplung von Abstraktion und Implementierung. Sie sind unabhängig voneinander und beeinflussen sich nicht gegenseitig.
  • 2. Für zwei sich unabhängig ändernde Dimensionen könnte das Bridge-Muster nicht besser geeignet sein.
  • 3. Änderungen an der "konkreten abstrakten Klasse" haben keine Auswirkungen auf Clients.

Original-URL: https://www.cnblogs.com/chenssy/3317866.html