python yield: send, close, throw
send
1. yield可以产出值,可以接收值
2. 在调用send发送非none值之前,我们必须启动一次生成器, 方式有两种
a. gen.send(None)
b. next(gen)
def gen_func(): #1. 可以产出值, 2. 可以接收值(调用方传递进来的值) html = yield 1 print(html) yield 2 yield 3 return "bobby" #1. 生成器不只可以产出值,还可以接收值 if __name__ == "__main__": gen = gen_func() #在调用send发送非none值之前,我们必须启动一次生成器, 方式有两种1. gen.send(None), 2. next(gen) url = gen.send(None) #download url html = "bobby" print(gen.send(html)) #send方法可以传递值进入生成器内部,同时还可以重启生成器执行到下一个yield位置 print(gen.send(html))
close
不要随便try catch
def gen_func(): yield "http://projectsedu.com" yield 2 yield 3 return "bobby" if __name__ == "__main__": gen = gen_func() print(next(gen)) gen.close() print(next(gen)) print("bobby")
如果要捕获异常,那么必须抛出StopIteration
def gen_func(): try: yield "http://projectsedu.com" except GeneratorExit: raise StopIteration yield 2 yield 3 return "bobby" if __name__ == "__main__": gen = gen_func() print(next(gen)) gen.close() print(next(gen)) print("bobby")
throw
在yield地方进行捕捉,而不是下一个yield;生成器在return的时候会抛出一个StopIteration,这个异常会一直向上抛出(跟普通的异常一样向上抛出)
def gen_func(): #1. 可以产出值, 2. 可以接收值(调用方传递进来的值) try: yield "http://projectsedu.com" except Exception as e: pass try: yield 2 except Exception as e: pass yield 3 return "bobby" if __name__ == "__main__": gen = gen_func() print(next(gen)) gen.throw(Exception, "download error") # 实际是 yield "http://projectsedu.com" 抛出异常
print(next(gen))
gen.throw(Exception, "download error1")