• 关于python协程的一个例子的学习


    例子来自https://blog.tonyseek.com/post/event-manage-with-greenlet/

    加了一些注释看懂了:

    注释中的数字表示执行的顺序,这个简单的例子用到了python自带的生成器,关键的地方是:调用生成器的模块使用next()时就开始执行生成器中的语句,生成器执行到yield 的地方会挂起,同时返回yield的值给调用模块。当执行fire_event('click')时,会实现另外一个next(),这时生成器得到信号,从挂起的地方开始执行,直到结束。而在响应函数resume()中next()没有收到yield返回的值,所以会发生StopIteration异常.从而结束整个程序

    #!/usr/bin/env python
    #coding=utf-8
    
    from time import sleep
    
    event_listeners = {}
    
    def fire_event(name):
    	event_listeners[name]()
    
    def use_event(func):
    	def call(*args, **kwargs):
    		print 'use_event' ## 1
    		generator = func(*args, **kwargs) ## 2
    		print 'come here' ## 3
    		event_name = generator.next() ## 4 开启generator,期待其返回一个yield()的值
    		print 'no wait here' ## 7	
    
    		def resume():
    			try:
    				print 'second time' ## 10
    				next(generator)  ##唤醒了test_work(),期待返回一个yield(),但是test_work只有一个yield(),所以这里会出现异常
    			except StopIteration:
    				print "test_work() doesn't have another yield()" ## 11
    				pass
    		event_listeners[event_name] = resume
    		print 'register !!' ## 8
    	return call
    
    @use_event
    def test_work():
    	print 'wait' ## 5
    	sleep(2)
    	yield 'click'# 6 执行至此,返回'click'给use_event中的next();test_work()挂起,等待另一个next()唤醒
    	print 'click.'
    	
    if __name__ == '__main__':
    	test_work()
    	sleep(3)
    	fire_event('click')#9  唤醒test_work()
    

  • 相关阅读:
    nginx 下 bootstrap fa 字体异常问题
    centos7 & mysql
    ssh authentication魔鬼细节--.ssh文件夹权限
    python self introspection
    __getattr__ 与动态属性
    dict.items vs six.iteritems
    django ATOMIC_REQUESTS
    HDU 4309 Seikimatsu Occult Tonneru (状压 + 网络流)
    UVaLive 4064 Magnetic Train Tracks (极角排序)
    UVa 11645 Bits (暴力+组合数学)
  • 原文地址:https://www.cnblogs.com/ylan2009/p/4202581.html
Copyright © 2020-2023  润新知