设计模式_18 责任链模式
18 责任链模式
18.1 概念
为了避免请求发送者与多个请求处理者耦合在一起,将所有请求的处理者通过前一对象记住其下一对象的引用而连成一条链。有请求发生时,可将请求沿着这条链传递,直到有对象处理为止。
18.2 结构
抽象处理者角色:定义一个处理请求的接口,包含抽象处理方法和一个后继连接。
具体处理者角色:实现抽象处理者的处理方法,判断是否能够处理本次请求,可以则处理,否则将请求转给后继者。
客户类角色:创建处理链,并向链头的具体处理者对象提交请求,不关心处理细节和具体的传递过程。
18.3 实现
18.3.1 UML图
18.3.2 代码
#include<iostream>
#include<string>
#include<list>
using namespace std;
class LeaveRequest {
private:
string name;
int num;
string content;
public:
LeaveRequest(string name, int num, string content) {
this->name = name;
this->num = num;
this->content = content;
}
string getName() {
return this->name;
}
int getNum() {
return this->num;
}
string getContent() {
return this->content;
}
};
class Handler {
protected:
int maxNum;
Handler* nextHandler = nullptr;
public:
Handler(int maxNum) {
this->maxNum = maxNum;
}
void setNextHandler(Handler* nextHandler) {
this->nextHandler = nextHandler;
}
virtual void handleLeave(LeaveRequest* request) = 0;
};
class HandlerLevelOne : public Handler {
public:
HandlerLevelOne(int maxNum) : Handler(maxNum) {}
void handleLeave(LeaveRequest* request) {
if (request->getNum() > this->maxNum) {
nextHandler->handleLeave(request);
}
else {
cout << "One级别批准 " << endl;
cout << "姓名:" << request->getName() << endl;
cout << "天数:" << request->getNum() << endl;
cout << "原因:" << request->getContent() << endl;
}
}
};
class HandlerLevelTwo : public Handler {
public:
HandlerLevelTwo(int maxNum) : Handler(maxNum) {}
void handleLeave(LeaveRequest* request) {
if (request->getNum() > this->maxNum) {
nextHandler->handleLeave(request);
}
else {
cout << "Two级别批准:" << endl;
cout << "姓名:" << request->getName() << endl;
cout << "天数:" << request->getNum() <<endl;
cout << "原因:" << request->getContent()<< endl;
}
}
};
class HandlerLevelThree : public Handler {
public:
HandlerLevelThree(int maxNum) : Handler(maxNum) {}
void handleLeave(LeaveRequest* request) {
if (request->getNum() > this->maxNum) {
cout<<"不批准" << request->getName() <<"的假期" << endl;
}
else {
cout << "Three级别批准 " << endl;
cout << "姓名:" << request->getName() << endl;
cout << "天数:" << request->getNum() << endl;
cout << "原因:" << request->getContent() << endl;
}
}
};
int main() {
Handler* one = new HandlerLevelOne(3);
Handler* two = new HandlerLevelTwo(7);
Handler* three = new HandlerLevelThree(30);
one->setNextHandler(two);
two->setNextHandler(three);
LeaveRequest* request = new LeaveRequest("张三", 10, "探亲");
one->handleLeave(request);
request = new LeaveRequest("李四", 360, "度假");
one->handleLeave(request);
return 0;
}
18.4 优缺点
18.4.1 优点
降低了对象之间的耦合度。
增强了系统的可扩展性。可以根据需要增加新的请求处理类,满足开闭原则。
增强了给对象指派职责的灵活性。当工作流程发生变化,可以动态修改链内成员或责任顺序。
简化了对象之间的连接。一个对象只保持一个指向其后继的引用。
责任分担。每个类只需要负责自己该处理的工作,不能处理则传递给下一个,符合单一职责原则。
18.4.2 缺点
不能保证每个请求一定会被处理。
对比较长的职责链,处理请求可能涉及多个对象,影响系统性能。
职责链建立的合理性需要客户端保证,增加了客户端的复杂性。职责链设置错误可能会导致循环调用。