定义
责任链模式(Chain of Responsibility Pattern)中,有一条由请求处理者对象组成的链条,每个对象(除最后一个对象外)都持有下一个对象的引用,请求发送者将请求发送给第一个对象,请求就会顺着链条走下去,直到有对象能够处理请求。该模式将多个处理者对象解耦,使得请求发送者只管将请求发送给责任链的第一个对象就是了,不用去关心请求具体是如何被处理的。
组成
抽象请求处理者(Abstract Request Handler):定义处理请求的接口。
具体请求处理者(Concrete Request Handler):持有下一个处理者对象的引用,具体实现处理请求的接口,包括将请求处理掉和传给下一个对象。
客户端(Client):将请求发送给责任链的头部对象。
举例
某学校的学生请假审批流程:
天数 <= 3:班主任审批通过;
3 < 天数 <= 7:班主任审批不通过,交给年级组长,年级组长审批通过;
7 < 天数 <= 30:年级组长审批不通过,交给教务处,教务处审批通过;
30 < 天数 <= 60:教务处审批不通过,交给校长,校长审批通过;
天数 > 60:校长审批不通过。
不用责任链模式写出的代码:
void handleRequest(int days)
{
if (days <= 3)
{
cout << "班主任审批通过。" << endl;
}
else
{
cout << "班主任审批不通过。交给年级组长。" << endl;
if (days <= 7)
{
cout << "年级组长审批通过。" << endl;
}
else
{
cout << "年级组长审批不通过。交给教务处。" << endl;
if (days <= 30)
{
cout << "教务处审批通过。" << endl;
}
else
{
cout << "教务处审批不通过。交给校长。" << endl;
if (days <= 60)
{
cout << "校长审批通过。" << endl;
}
else
{
cout << "校长审批不通过。" << endl;
}
}
}
}
}
可以看到,这段代码又是一堆if-else又是层层嵌套的,又臭又长,好难看!更重要的问题是,如果流程需要修改,那业务代码也需要修改,不符合开闭原则,难以维护和扩展。
那怎么样提高程序的可扩展性呢?
我们应该把班主任、年级组长等等拆分出来当做请求处理者,并指定一个共同的抽象父类,父类里面定义抽象接口,子类具体实现这些接口。
UML类图:
代码:
/** 抽象处理者 */
class AbstractRequestHandler
{
protected:
AbstractRequestHandler *const nextHandler; // 由于链条中最后一个处理者没有下一个处理者,但是c++不像java那样存在空引用,所以只能用指针了
const int maxDaysLimit;
const char *name;
virtual void handleRequest(int days)
{
if (days <= maxDaysLimit)
{
cout << name << "审批通过" << endl;
}
else
{
cout << name << "审批不通过" << endl;
if (nextHandler)
{
cout << "转交给" << nextHandler->name;
nextHandler->handleRequest(days);
}
}
}
virtual ~AbstractRequestHandler()
{
if (nextHandler)
{
delete nextHandler;
}
}
}
/** 具体处理者————校长 */
class Principal : public AbstractRequestHandler
{
public:
Principal() :
nextHandler(nullptr),
maxDaysLimit(60),
name("校长")
{ }
}
/** 具体处理者————教务处 */
class AcademicAffairsOffice : public AbstractRequestHandler
{
public:
AcademicAffairsOffice() :
nextHandler(new Principal),
maxDaysLimit(30),
name("教务处")
{ }
}
// 年级组长、班主任 略
/** 客户端 */
class Client
{
HeadTeacher &headTeacher;
void sendRequest(int days)
{
headTeacher.handleRequest();
}
}
int main()
{
Client client;
client.sendRequest();
return 0;
}
标签:请求,处理,days,模式,责任,对象,int,nextHandler,设计模式
From: https://www.cnblogs.com/YWT-Real/p/16730326.html