yield关键字执行流程
注意:yield关键字的调用次数如果超过了任务执行次数会报错,提示stopiteration异常,例如
正常范围内的任务执行
# 定义一个任务(函数1)
def task1():for i in range(3):print(f'----task1 i = {i}----')# yield 关键字会造成当前函数称为一个生成器对象# yield 会将当前任务函数挂起,不继续向下执行,CPU不再回等待挂起结束的任务yield# 定义一个任务(函数2)
def task2():for i in range(3):print(f'----task2 i = {i}----')yieldif __name__ == '__main__':# 现在的程序只有一条主线程(IO并发操作)# 任务(函数)t1 = task1() # task1()不是调用函数,函数中只要有yield关键字,就变成了返回生成器对象t2 = task2()# <generator object task1 at 0x0000025C5A565A80># print(t1)# <generator object task2 at 0x0000025C5A567C40># print(t2)# 如果是一个生成器对象,函数如何执行?# yield关键字需要配合 next 内置函数实现调用next(t1)next(t2)# 第二次调用next(t1)next(t2)# 第三次调用next(t1)next(t2)# 第四次调用# next(t1)# next(t2)
执行结果
生成器取值的三种方式(next、循环+next、循环)
# 1,1,2,3,5,8,13,21,34...斐波那契数列,后面第三个数是前两个数和# 生成器对象,使用了yield关键字,当前函数已经成为了生成器对象
def fibonacci(n):a,b = 1,1current_n = 0while current_n < n:yield aa, b = b, a + bcurrent_n += 1# 退出循环,已经完成了执行,让函数返回一个结果# 最终生成器的返回结果是在发生异常的时候返回的return 'done'if __name__ == '__main__':v = fibonacci(5)print(v)print(next(v))print(next(v))print(next(v))print(next(v))print(next(v))# print(next(v)) StopIteration: doneprint('-' * 20)v2 = fibonacci(5)while True:try:g = next(v2)print(g)except StopIteration as e:print(e) # 这里的e就是生成器的一场结果break# 生成器对象就是一个可迭代对象print('-' * 20)for i in fibonacci(5):print(i)
执行结果