Policy Mode
Behavioral patterns
In Strategy Pattern, the behavior of a class or its algorithm can be changed at run time.
In policy mode, we create an object representing various policies and a context object whose behavior changes as the policy object changes. The policy object changes the execution algorithm of the context object.
introduce
Intention: Define a series of algorithms, encapsulate them one by one, and make them interchangeable.
Main Solution: In cases where there are many similar algorithms, use if...else is complex and difficult to maintain.
When to use: A system has many classes, and what distinguishes them is their direct behavior.
How to solve this problem: encapsulate these algorithms into one class after another and replace them arbitrarily.
Key Code: Implement the same interface.
Specific implementation
Step 1: Create a Duck Behavior Interface
public interface QuackBehavior { void quack(); }
public interface FlyBehavior { void fly(); }
Step 2: Create an implementation of the specific behavior
public class BadFlyBehavior implements FlyBehavior { @Override public void fly() { System.out.println("Flying technology is general"); } }
public class GoodFlyBehavior implements FlyBehavior { @Override public void fly() { System.out.println("High-tech flight"); } }
public class NoFlyBehavior implements FlyBehavior { @Override public void fly() { System.out.println("Duck that Can't Fly"); } }
Step 3: Create an abstract duck class
public abstract class Duck { //Property, Policy Interface FlyBehavior flyBehavior; //Other Properties <->Policy Interfaces QuackBehavior quackBehavior; public Duck() { } public abstract void display();//Show duck information public void quack() { System.out.println("quack~~"); } public void swim() { System.out.println("A duck can swim~~"); } public void fly() { //Improvement if (flyBehavior != null) { flyBehavior.fly(); } } public void setFlyBehavior(FlyBehavior flyBehavior) { this.flyBehavior = flyBehavior; } public void setQuackBehavior(QuackBehavior quackBehavior) { this.quackBehavior = quackBehavior; } }
Step 4: Create different kinds of ducks
public class PekingDuck extends Duck { //If Peking Duck can fly, but the flight technology is general public PekingDuck() { flyBehavior = new BadFlyBehavior(); } @Override public void display() { System.out.println("~~Peking duck~~~"); } }
public class ToyDuck extends Duck { public ToyDuck() { flyBehavior = new NoFlyBehavior(); } @Override public void display() { System.out.println("Toy duck"); } @Override public void quack() { System.out.println("A toy duck cannot bark~~"); } @Override public void swim() { System.out.println("Toy duck can't swim~~"); } }
public class WildDuck extends Duck { //Constructor, object passed into FlyBehavor public WildDuck() { flyBehavior = new GoodFlyBehavior(); } @Override public void display() { System.out.println(" This is a wild duck "); } }
Step 5: Create a test class
public class Client { public static void main(String[] args) { WildDuck wildDuck = new WildDuck(); wildDuck.fly();// ToyDuck toyDuck = new ToyDuck(); toyDuck.fly(); PekingDuck pekingDuck = new PekingDuck(); pekingDuck.fly(); //Dynamic change of an object's behavior, Peking Duck can't fly pekingDuck.setFlyBehavior(new NoFlyBehavior()); System.out.println("Actual Flying Capability of Peking Duck"); pekingDuck.fly(); } }
Run as follows:
High-tech flight Duck that Can't Fly Flying technology is general Actual Flying Capability of Peking Duck Duck that Can't Fly
Advantage:
1. The algorithm can switch freely.
2. Avoid using multiple conditional judgments.
3. Good scalability.
Disadvantages:
1. There will be more strategic categories.
2. All policy classes need to be exposed.