Python设计模式(六)【职责链模式】
来源:互联网 发布:北大知乎 编辑:程序博客网 时间:2024/05/22 13:33
周末补充知识,编程哲学
"""职责链模式"""import timeimport osimport sysfrom contextlib import contextmanager"""象处理者:定义出一个处理请求的接口。如果需要,接口可以定义出一个方法,以设定和返回对下家的引用。这个角色通常是一个抽象类或接口。"""class Handler: def __init__(self, successor=None): self._successor = successor def handle(self, request): res = self._handle(request) if not res: self._successor.handle(request) def _handle(self, request): raise NotImplementedError('必须提供子类实现.')#实际处理者1class ConcreteHandler1(Handler): def _handle(self, request): if 0 < request <= 10: print('请求{} 被处理程序1 处理'.format(request)) return True#实际处理者2class ConcreteHandler2(Handler): def _handle(self, request): if 10 < request <= 20: print('请求{} 被处理程序2 处理'.format(request)) return True#实际处理者3class ConcreteHandler3(Handler): def _handle(self, request): if 20 < request <= 30: print('请求{} 被处理程序3 处理'.format(request)) return True#默认处理者class DefaultHandler(Handler): def _handle(self, request): print('职责链已到终点,没有处理程序处理{}'.format(request)) return True""" 这里用到了yield,然后就可以直接将接收到的数据打印出来了。当然,还有一个值得注意的地方是用到了一个@coroutine的decorator。 因为在每次使用coroutine之前我们需要调用一次target.next()或者target.send(None)来初始化它。这样我们使用的时候很容易忘记这一步, 一种办法就是定义好一个这样的decorator,然后每次将这个decorator加上就保证这一步被执行了。@coroutine decorator的定义如下: 如果是函数定义中参数前的*表示的是将调用时的多个参数放入元组中,**则表示将调用函数时的关键字参数放入一个字典中 如定义以下函数 def func(*args):print(args) 当用func(1,2,3)调用函数时,参数args就是元组(1,2,3) 定义以下函数 def func(**args):print(args) 当用func(a=1,b=2)调用函数时,参数args将会是字典{'a':1,'b':2}"""def coroutine(func): def start(*args, **kwargs): cr = func(*args, **kwargs) next(cr) return cr return start"""coroutine是一个实现多个任务之间互相切换的手段,它相当于一种将一个当前执行的结果传递给另外一个过程。和generator的使用过程比起来,它更像是一种“推”模式。因为我们要使用一个coroutine的时候,必然是需要有其它的过程send数据过来。因为yield的过程有点类似于一个操作系统里中断的概念,它相当于将一个进程的当前执行过程暂停,然后跳转到另外一个过程。这种过程和我们传统通过栈实现的子过程调用很不一样,所以表面上理解起来还是有点困难。因为coroutine相当于一个数据的消费者协同程序(协程)一般来说是指这样的函数: 彼此间有不同的局部变量、指令指针,但仍共享全局变量; 可以方便地挂起、恢复,并且有多个入口点和出口点; 多个协同程序间表现为协作运行,如A的运行过程中需要B的结果才能继续执行。"""@coroutinedef coroutine1(target): while True: #接收行 request = yield if 0 < request <= 10: print('请求{}在被协同程序1 处理 '.format(request)) else: target.send(request)@coroutinedef coroutine2(target): while True: request = yield if 10 < request <= 20: print('请求{}在被协同程序2 处理'.format(request)) else: target.send(request)@coroutinedef coroutine3(target): while True: request = yield if 20 < request <= 30: print('请求{}在被协同程序3 处理'.format(request)) else: target.send(request)@coroutinedef default_coroutine(): while True: request = yield print('职责链的终点,没有协同程序处理{}'.format(request))"""客户端协程"""class ClientCoroutine: def __init__(self): self.target = coroutine1(coroutine3(coroutine2(default_coroutine()))) def delegate(self, requests): for request in requests: """发送到下一个阶段""" self.target.send(request)def timeit(func): def count(*args, **kwargs): start = time.time() res = func(*args, **kwargs) count._time = time.time() - start return res return count"""上下文管理器(Context Manager):支持上下文管理协议的对象,这种对象实现了__enter__() 和 __exit__() 方法。上下文管理器定义执行 with 语句时要建立的运行时上下文,负责执行 with 语句块上下文中的进入与退出操作。"""@contextmanagerdef suppress_stdout(): try: stdout, sys.stdout = sys.stdout, open(os.devnull, 'w') yield finally: sys.stdout = stdoutclass Client: def __init__(self): self.handler = ConcreteHandler1(ConcreteHandler3(ConcreteHandler2(DefaultHandler()))) def delegate(self, requests): for request in requests: self.handler.handle(request)if __name__ == "__main__": client1 = Client() client2 = ClientCoroutine() requests = [2, 5, 14, 22, 18, 3, 35, 27, 20] client1.delegate(requests) print('-' * 30) client2.delegate(requests) requests *= 10000 #数组增加到9W个 #print(requests) client1_delegate = timeit(client1.delegate) client2_delegate = timeit(client2.delegate) with suppress_stdout(): client1_delegate(requests) client2_delegate(requests) # 让我们检查哪个速度更快 print("类处理时间:",client1_delegate._time,"协同程序处理时间:",client2_delegate._time)
结果如图:
0 0
- Python设计模式(六)【职责链模式】
- Python设计模式-职责链模式
- Java技术常用设计模式(六)--- 职责链模式
- 职责链设计模式
- 【设计模式】职责链
- 设计模式---职责链
- 职责链设计模式
- 职责链设计模式
- 职责链模式(python)
- 设计模式---职责链模式
- 设计模式-职责链模式
- 设计模式 职责链模式
- 设计模式- 职责链模式
- 设计模式 - 职责链模式
- 设计模式 - 职责链模式
- 设计模式-职责链模式
- 设计模式--职责链模式
- 设计模式-职责链模式
- 开发人员不可不知的六大JavaScript框架 传统网站网页转移动端方式
- 为什么现在又想开始写技术博客了?
- GitHub 出现 POST git-receive-pack (chunked) 解决方案详解
- nutch源码分析---7
- 【Hibernate】--关联关系映射:一对一关联
- Python设计模式(六)【职责链模式】
- uboot环境变量(设置bootargs向linux内核传递正确的参数)
- 解决app一打开白屏和黑屏的问题
- 移动站原生的select实现省市区联动选择
- linux之early_param()和__setup
- STM32之CAN---发送管理分析
- 使用jQuery Mobile移动开发框架将博客网站快速转化为Mobile网站
- string - memcpy源码
- Dlib机器学习库编译以及安装