Ist die Kontextvererbung, wie im Beispiel Duck von Head First Design Patterns gezeigt, für das Strategiemuster irrelevant?


10

In Head First Design Patterns wird das Strategiemuster anhand eines Duck-Beispiels vermittelt, bei dem verschiedenen Duck-Unterklassen zur Laufzeit ein bestimmtes Verhalten zugewiesen werden kann. Nach meinem Verständnis besteht der Zweck des Strategiemusters darin, das Verhalten eines einzelnen Objekts zur Laufzeit zu ändern. Sie verwenden jedoch die Vererbung von Duck, um das Verhalten verschiedener Ententypen zu ändern.

Strategiemuster

Relevanz?

Ist die Kontextvererbung von Duck für das Strategiemuster irrelevant oder sind unterschiedliche Ententypen und auch deren Verhalten ein guter Grund, das Strategiemuster anzuwenden? Sind Situationen, in denen Sie beide variieren müssen, ein guter Grund, ein Strategiemuster zu verwenden? Warum sollten sie dies als Beispiel für ein Strategiemuster aufnehmen?

Ein einfacheres Beispiel

Könnte ich dieses Beispiel weiter vereinfachen, indem ich nur eine Entenklasse habe (keine abgeleiteten Klassen)? Wenn dann ein Entenobjekt implementiert wird, kann es aufgrund bestimmter Umstände, die nicht von seinem eigenen Objekttyp abhängen, unterschiedlichen Verhaltensweisen zugewiesen werden. Zum Beispiel: FlyBehavior ändert sich je nach Wetterlage oder QuackBehavior ändert sich je nach Tageszeit oder wie hungrig eine Ente ist. Mir ist klar, dass dies ein anderes Problem lösen würde als das im Buch, aber ich suche nach einem relevanten Beispiel für ein Strategiemuster, auf das ich zurückgreifen kann.

Würde mein obiges Beispiel auch das Strategiemuster darstellen?

Bearbeiten:

Es ist mir gelungen, zwei einfachere Beispiele für Strategiemuster zu finden, die strenger darauf abzielen , nur Strategiemuster ohne Kontextvererbung zu sein: Hunter.java und solver.py .

Antworten:


7

Ja, ich denke du bist auf dem richtigen Weg. Die Klasse, die das Strategiemuster verwendet, muss keine Unterklasse sein. Das Strategiemuster ist eine Alternative zur Vererbung für die Wiederverwendung von Code. Dies kommt auf den noch umfassenderen Vergleich von Vererbung und Zusammensetzung zurück.

Aus Entwurfsmustern: Elemente von wiederverwendbarem OOP würden Sie Strategiemuster verwenden, um

  • Vermeiden Sie eine Explosion von Unterklassen (aufgrund von Verhaltenskombinationen).
  • Wenn Sie das Verhalten zur Laufzeit austauschen müssen

Wenn Sie die Vererbung verwenden, um Quack- und Fly-Verhalten zu implementieren, würden Sie mit all diesen Unterklassen alle Verhaltenskombinationen darstellen.

  • FlyableQuackableDuck
  • FlyableSqeakableDuck
  • FlyableMuteDuck
  • NoFlyQuackableDuck
  • NoFlySqueakableDuck
  • NoFlyMuteDuck

Bei so vielen Unterklassen ist es schwieriger, diese beizubehalten, weshalb in diesem Fall das Strategiemuster bevorzugt wird. Sie benötigen lediglich zwei Eigenschaften, die Flyability und Quackability einschließen, und Sie können diese mischen und anpassen, ohne neue Klassen zu erstellen.

Sie haben auch bereits den Laufzeitvorteil erwähnt, dass die Fly-Eigenschaft der Ente aufgrund der Bedingungen durch ein NoFly-Objekt ersetzt werden könnte, wenn sich das Wetter ändert.

Dies steht im Einklang mit dem Rat, die Zusammensetzung nach Möglichkeit der Vererbung vorzuziehen.


1

Könnte ich dieses Beispiel weiter vereinfachen, indem ich nur eine Entenklasse habe (keine abgeleiteten Klassen)? Wenn dann ein Entenobjekt implementiert wird, kann es aufgrund bestimmter Umstände, die nicht von seinem eigenen Objekttyp abhängen, unterschiedlichen Verhaltensweisen zugewiesen werden.

Bestimmt. Inspiration finden Sie in Head First Object-Oriented Analysis and Design . Es gibt eine "Rick's Guitars", die eine Explosion von (Musik-) Instrumenten -Unterklassen zeigt. Um dies zu beheben, wird das unterschiedliche Verhalten in eine "Spezifikations" -Klasse eingeschlossen, wobei das Prinzip der Verkapselung des Variierenden beachtet wird .

Abstrakte Fabrik - Kontextbasierte Konstruktion

Hier ist das Muster . Übrigens, beachten Sie, dass es Strategie selbst verwendet.

Konzentrieren Sie sich auf das Konzept, nicht auf die Implementierung ... Möglicherweise verfügen Sie über eine "WeatherFactory", die Spezifikationsobjekte basierend auf sonnigen oder regnerischen Bedingungen usw. erstellt.

Sie könnten "Fabriken von Fabriken" haben, um diese "NoFlyInFogQuackableMallard" -Dingies zu konstruieren. Und genau darum geht es im Abstract Factory-Muster. Also vielleicht eine Entenfabrik, um allgemeine Ententypen herzustellen, dann eine Wetterfabrik, um ihr ententypspezifisches Nebelwetterverhalten zu verleihen.

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.