10 - Design Patterns - Chain of Responsibility Pattern

Chain of Responsibility Pattern Concept

First, let's take a look at the introduction to the chain of responsibility model from the rookie tutorial

Intent: To avoid coupling request sender and receiver, make it possible for multiple objects to receive the request, connect these objects into a chain, and pass the request along the chain until an object handles it.

Main solution: The handler on the chain of responsibility is responsible for processing the request. The client only needs to send the request to the chain of responsibility, and does not need to care about the processing details of the request and the delivery of the request. Therefore, the chain of responsibility connects the sender of the request and the handler of the request. decoupled.

When to use: When processing messages to filter multiple channels.

How to solve: The intercepted classes all implement the unified interface.

Key code: Handler aggregates itself, judges whether it is suitable in HanleRequest, if it does not meet the conditions, it will be passed down, and set it in before passing it to whom
.

Application examples:
1. "Drumming and Passing Flowers" in Dream of Red Mansions.
2. Event bubbling in JS.
3. The processing of Encoding by Apache Tomcat in JAVA WEB, the interceptor of Struts2, and the Filter of jsp servlet.

Advantages:
1. Reduce coupling. It decouples the sender and receiver of requests.
2. Simplify the object. Makes the object not need to know the structure of the chain.
3. Enhance the flexibility of assigning responsibilities to objects. Allows responsibilities to be dynamically added or removed by changing members within the chain or reordering them.
4. It is very convenient to add a new request processing class.

Disadvantages:
1. There is no guarantee that the request will be received.
2. The system performance will be affected to a certain extent, and it is inconvenient to debug the code, which may cause cyclic calls.
3. It may not be easy to observe the characteristics of the runtime, which hinders debugging.

Usage scenarios:
1. There are multiple objects that can process the same request, and which object processes the request is automatically determined by the runtime.
2. Submit a request to one of multiple objects without explicitly specifying the recipient.
3. A group of objects can be dynamically specified to process requests.

Note: Many applications are encountered in JAVA WEB.

case

Ok, after reading the above introduction, I think I have a certain concept of the chain of responsibility model, so let's write a case and see the following.
It is known that Xiao Ming is going to ask for leave. He first sends a leave request to the group leader. The group leader does not have the approval authority and submits the leave request to the monitor. The monitor also has no approval authority, and submits the leave request to the teacher. The teacher has the approval authority to reply.

Handler

Abstract handler, here refers to the abstract interface of all handlers in the chain of responsibility. It has two methods, one is to accept the request and process it; one is to pass the request to the next handler.

public interface Handler {

    List<Handler> list = new ArrayList<>();

    /**
     * 接受请假请求,并进行处理
     * @return void
     * @param people
     * 时间:2018年4月26日
     */
    public void handle(People people);

    /**
     * 获取下一个处理器
     * @return Handler
     * @return
     * 时间:2018年4月26日
     */
    public Handler getHandler();
}

ConcreteHandler

public class AHandler implements Handler {

    @Override
    public void handle(People people) {
        if (1 == people.getLeave()) {
            System.out.println("A:批准");
        } else {
            Handler handler = getHandler();
            if (null == handler) {
                System.out.println("请求未批准");
            } else {
                handler.handle(people);
            }
        }
    }

    @Override
    public Handler getHandler() {
        // 判断list中是否存在元素
        if (list.size() <= 0) {
            return null;
        }
        // 对list进行遍历
        for (int i = 0; i < list.size() - 1; i++) {
            // 判断i位置元素是否等于当前元素,true则返回下一个元素
            if (list.get(i) == this) {
                    return list.get(i + 1);
            }
        }
        return null;
    }

}
public class BHandler implements Handler{
    @Override
    public void handle(People people) {
        if (2 == people.getLeave()) {
            System.out.println("B:批准");
        } else {
            Handler handler = getHandler();
            if (null == handler) {
                System.out.println("请求未批准");
            } else {
                handler.handle(people);
            }
        }
    }

    @Override
    public Handler getHandler() {
        // 判断list中是否存在元素
        if (list.size() <= 0) {
            return null;
        }
        // 对list进行遍历
        for (int i = 0; i < list.size() - 1; i++) {
            // 判断i位置元素是否等于当前元素,true则返回下一个元素
            if (list.get(i) == this) {
                    return list.get(i + 1);
            }
        }
        return null;
    }
}
public class CHandler implements Handler {

    @Override
    public void handle(People people) {
        if (3 == people.getLeave()) {
            System.out.println("C:批准");
        } else {
            Handler handler = getHandler();
            if (null == handler) {
                System.out.println("请求未批准");
            } else {
                handler.handle(people);
            }
        }
    }

    @Override
    public Handler getHandler() {
        // 判断list中是否存在元素
        if (list.size() <= 0) {
            return null;
        }
        // 对list进行遍历
        for (int i = 0; i < list.size() - 1; i++) {
            // 判断i位置元素是否等于当前元素,true则返回下一个元素
            if (list.get(i) == this) {
                    return list.get(i + 1);
            }
        }
        return null;
    }
}

Request

public class People {

    /**
     * 代表了请假请求发送者的级别
     */
    private int leave;

    public int getLeave() {
        return leave;
    }

    public void setLeave(int leave) {
        this.leave = leave;
    }


}

test class

public class Test {
    public static void main(String[] args) {
        People people = new People();
        people.setLeave(3);
        Handler handler = new AHandler();
        Handler handler2 = new BHandler();
        Handler handler3 = new CHandler();
        handler.list.add(handler);
        handler.list.add(handler2);
        handler.list.add(handler3);
        handler.handle(people);
    }
}

Guess you like

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