Introduction to 23 Design Patterns (2) ---- Introduction to 23 Design Patterns of Structural Patterns (2) ---- Structural Patterns

Due to the large space of design patterns, it is not conducive to reading if all design patterns are covered in one article. So I divided it into three articles

  Design patterns are relatively abstract concepts, so you must ensure that you understand the class diagram before writing code to strengthen your memory.

Overview

  There are seven structural patterns:

  • Adapter mode (Adapter)        
  • Facade
  • Bridge Mode (Bridge)
  • Decorator pattern (Decorator)
  • Proxy mode (Proxy)
  • Flyweight
  • Composite mode

  which is divided into

  Interface adaptation: adapter, appearance, bridge mode

  Behavior extension: decoration

  Performance and Object Access: Proxies, Flyweight Patterns

  Abstract Collections: Composition Patterns

1. Adapter mode

  Definition: Convert the interface of a class into another interface that the client wants. The Adapter pattern makes those classes that could not work together because of incompatible interfaces work together.

  Role: adapter (Adapter), adapted class, object (Adaptee)

  Understanding: Customers need Target, but in reality there is only Adaptee. You can use an adapter that implements the Target protocol to obtain Adaptee through class inheritance or object composition class.

  Class Diagram:

  

  Example code:

copy code
// The original interface does not meet customer requirements 
interface IOrigin{ public void deal(); }
// Define a new interface that meets the client's requirements interface ITarget{ public void newDeal(int type); } class Target implements ITarget{ private IOrigin origin; public void newDeal(int type){ if (type==0){ origin.deal(); }else{ // do other } } } public class TestAdapter { public void test(){ // It turned out to be the IOrigin interface but it did not meet my requirements, so I used ITarget to adapt it // ITarget target = new Target(); target.newDeal(1); } }
copy code

2. Appearance mode

  Definition: Provide a unified interface for a set of different interfaces in a subsystem

  When to use: 1. Subsystems are gradually becoming more complex, and many classes have evolved in the process of applying patterns. Facades can be used to provide a simpler interface to these subsystem classes. 2. Subsystems can be layered using appearances, each character system level has an appearance as an entry. Having them communicate via appearance simplifies their dependencies.

  Class Diagram:

  Example code:

copy code
// A maintenance car factory system includes, car maintenance, bus maintenance, acceptance
// cart
class Car{
    // repair
    public void repair();
}
// bus
class Bus{
    // repair
    public void repair();
}
// Maintenance staff
class Repairer{
    public void doRepair();
}
// Acceptance staff
class Checker{
    public void doCheck();
}

// The boss can't be so meticulous, he needs to hire a manager
class Leader{
    private Repairer repairer;
    private Checker checker;
    public void repair();
    public boolean check();
}
public class TestFacade {
    public void test(){
        // When the boss receives an order, he directly asks the manager to repair the car, and then asks the manager if it has been completed. The manager is just an appearance
        Leader leader = new Leader();
        // Notify the manager to repair the car, no matter how many maintenance personnel there are under the manager, the acceptance personnel
        leader.repair();
        boolean isOk = leader.check ();
    }
}
copy code

3. Bridge mode

  Definition: separate the abstract part from its implementation part so that it can be changed independently

  Role: abstraction layer interface (Abstraction), concrete abstraction layer, implementer interface, concrete implementer.

  Understanding: There are two interfaces here, one is the abstraction layer interface Abstraction, the other is the Implementor interface, where Abstraction holds a reference to Implementor. The client connects the Implementor through the Abstraction, and the Implementor can be changed dynamically in the future without affecting the Abstraction.  

  When to use: 1. Do not want to form a fixed binding relationship between the abstraction and the implementation (so that the implementation can be switched at runtime). 2. Both abstraction and implementation should be independently extendable through subclassing.
3. Modifications to the implementation of the abstraction should not affect client code. 4. If each implementation requires additional subclasses to refine the abstraction, it is necessary to split them into two parts. 5. Want to share an implementation among multiple objects with different abstract interfaces.

  Class Diagram:

  

  Example code:

copy code
ILeader interface {
    public void doSomething();
}
class LeaderA implements ILeader{
    @Override
    public void doSomething() {}
}
class LeaderB implements ILeader{
    @Override
    public void doSomething() {}
}
class Boss {
    Leader leader;
    public void setLeader(ILeader leader) {
        this.leader = leader;
    }
    public void doSomething(){
        this.leader.doSomething();
    }
}
public class TestBirdge {
    public void test(){
        Boss boss = new Boss();
        LeaderA leaderA = new LeaderA();
        boss.setLeader(leaderA);
        boss.doSomething();
        // When a manager leaves, the boss can find another experienced manager to do things,
        LeaderB leaderB = new LeaderB();
        boss.setLeader(leaderB);
        boss.doSomething();
    }
}
copy code

Fourth, the decorator mode

  Definition: Dynamically add some additional responsibilities to an object. Decorating is more flexible than subclassing in terms of adding functionality.

  Role: component interface (Component), specific component, decoration interface (Decorator) inherited from Component, specific decoration

  Understanding: The decoration interface Decorator inherits Component and holds a reference to Component, so it plays a role in reusing Component and adding new functions.

  When to use: 1. Want to add responsibilities to a single object in a dynamic and transparent way without affecting other objects. 2. Want to extend the behavior of a class, but can't. The class definition may be hidden from subclassing; or the extension of each behavior of the class, oh to support each combination of functions, will result in a large number of subclasses.

  Class Diagram:

 

  Example code:

copy code
interface ICar{
    public void run();
}
class Car implements ICar{
    @Override
    public void run() {

    }
}
// Now want to add nitrogen acceleration to the car
// The following is implemented by subclassing
class SubClassCar extends Car{
    @Override
    public void run() {
        this.addNitrogen();
        super.run();
    }
    public void addNitrogen(){}
}
// The following is implemented in the decoration mode
class DecoratorCar implements ICar{
    private Car car;
    @Override
    public void run() {
        this.addNitrogen();
        car.run();
    }
    public void addNitrogen(){}
}
public class TestDecorator {
    public void test(){
        
    }
}
copy code

 

 

5. Agency Mode

  Definition: Provides a proxy for other objects to control access to this object

  Role: client (Client), target interface (subject) proxy object (Proxy), real target object (RealSubject)

  Virtual proxy: The client has a reference to Subject, which is actually a Proxy object. The Proxy object holds a reference to RealSubject. Calling Proxy.request Proxy will actually call RealSubject.request

  Class Diagram:

 

  Example code:

copy code
// A customer wants to buy a house
class Customer{
    public void sellHouse(){
    }
}
class Proxy {
    private Customer customer;
    public void buyHouse(){
        customer.sellHouse();
    }
}
public class TestProxy {
    public void test(){
        // If a buyer wants to buy a house, he can directly deal with the intermediary (agent)
        Proxy proxy = new Proxy();
        proxy.buyHouse();
    }
}
copy code

 

6. Combination mode

  Definition: Groups objects into a tree structure to represent a 'part-whole' hierarchy. The composite mode allows users to use individual objects and composite objects consistently.

  Understanding: The composition pattern allows us to group objects of the same base type into a tree-like structure, where parent nodes contain child nodes of the same type.

  When to use: 1. Want to get a tree representation of object abstraction (part-whole hierarchy). 2. I want the client to uniformly process all the objects in the combined structure.
  Class Diagram:

7. Flyweight Mode

  Definition: Use sharing techniques to efficiently support a large number of fine-grained objects.

  Role: Flyweight Pool, Flyweight Interface, Specific Flyweight Object

  Understanding: When the client needs a flyweight object, it first goes to the flyweight pool to find it. If it is found, it will be reused directly. If it is not found, it will create a flyweight object and save it to the flyweight pool.

  Class Diagram:

 

Reference: Introduction to 23 Design Patterns (2) ---- Structural Patterns

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325154496&siteId=291194637