第24章:职责链模式
职责链模式
职责链(chain of responsibility)模式:使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系。将这个对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止。
Handler
类,定义一个处理请示的接口。
ConcreteHandler
类,具体处理者类,处理它所负责的请求,可访问它的后继者,如果可处理该请求,就处理之,否则就将该请求转发给它的后继者。
ConcreteHandler1
,当请求数在0到10之间则有权处理,否则转到下一位。
ConcreteHandler2
,当请求数在10到20之间则有权处理,否则转到下一位。
ConcreteHandler3
,当请求数在20到30之间则有权处理,否则转到下一位。
客户端代码,向链上的具体处理者对象提交请求。
职责链的好处
当客户提交-一个请求时,请求是沿链传递直至有一个ConcreteHandler
对象负责处理它。
接收者和发送者都没有对方的明确信息,且链中的对象自己也并不知道链的结构。结果是职责链可简化对象的相互连接,它们仅需保持一个指向其后继者的引用,而不需保持它所有的候选接受者的引用,大大降低了耦合度。
由于是在客户端来定义链的结构,也就是可以随时地增加或修改处理一个请求的结构,增强了给对象指派职责的灵活性。
注意:一个请求极有可能到了链的末端都得不到处理,或者因为没有正确配置而得不到处理。
职责链模式示例
任务:加薪逐级审批
from abc import ABCMeta, abstractmethod
from typing import Text
class Request(object):
"""
申请类
"""
def __init__(self) -> None:
# 申请类别
self.__request_type = None
# 申请内容
self.__request_content = None
# 申请数量
self.__number = None
@property
def request_type(self) -> Text:
return self.__request_type
@request_type.setter
def request_type(self, value: Text) -> None:
self.__request_type = value
@property
def request_content(self) -> Text:
return self.__request_content
@request_content.setter
def request_content(self, value: Text) -> None:
self.__request_content = value
@property
def number(self) -> Text:
return self.__number
@number.setter
def number(self, value: int) -> None:
self.__number = value
class Manager(metaclass=ABCMeta):
"""
管理者(Handler)类
"""
def __init__(self, name: Text) -> None:
self._name = name
self._superior = None
def set_superior(self, superior: object) -> None:
"""
设置管理者的上级
"""
self._superior = superior
@abstractmethod
def request_applications(self, request: Request) -> None:
"""
申请请求
"""
pass
class CommonManager(Manager):
"""
经理类
"""
def __init__(self, name: Text) -> None:
super(CommonManager, self).__init__(name)
def request_applications(self, request: Request) -> None:
"""
经理权限
"""
if (request.request_type == "请假") and (request.number <= 2):
print("{}:{},数量{},被批准".format(self._name, request.request_type, request.number))
else:
if self._superior:
self._superior.request_applications(request)
class Majordomo(Manager):
"""
总监类
"""
def __init__(self, name: Text) -> None:
super(Majordomo, self).__init__(name)
def request_applications(self, request: Request) -> None:
"""
总监权限
"""
if (request.request_type == "请假") and (request.number <= 5):
print("{}:{},数量{},被批准".format(self._name, request.request_type, request.number))
else:
if self._superior:
self._superior.request_applications(request)
class GeneralManager(Manager):
"""
总经理类
"""
def __init__(self, name: Text) -> None:
super(GeneralManager, self).__init__(name)
def request_applications(self, request: Request) -> None:
"""
经理权限
"""
if (request.request_type == "请假"):
print("{}:{},数量{},被批准".format(self._name, request.request_type, request.number))
elif (request.request_type == "加薪") and (request.number <= 500):
print("{}:{},数量{},被批准".format(self._name, request.request_type, request.number))
else:
print("{}:{},数量{},再说吧".format(self._name, request.request_type, request.number))
# 客户端调用
if __name__ == "__main__":
jinli = CommonManager("金利")
zongjian = Majordomo("宗剑")
zhongjingli = GeneralManager("钟精励")
jinli.set_superior(zongjian)
zongjian.set_superior(zhongjingli)
request = Request()
request.request_type = "请假"
request.request_content = "小菜请假"
request.number = 1
jinli.request_applications(request)
request.number = 4
jinli.request_applications(request)
request.request_type = "加薪"
request.request_content = "小菜加薪"
request.number = 500
jinli.request_applications(request)
request.number = 1000
jinli.request_applications(request)
金利:请假,数量1,被批准
宗剑:请假,数量4,被批准
钟精励:加薪,数量500,被批准
钟精励:加薪,数量1000,再说吧