生成器(yield函数)
yield介绍
带有yield的函数在Python中称为生成器(generator)
生成斐波那契(Fibonacci)数列是一个非常简单的递归数列,除第一个和第二个数外,任意一个数都可由前两个数相加得到。
列子1:
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| def A(max): a,b,c = 0,0,1 while a < max: print(C) b,c = c,b+c a = a +1 a(5)
结果:1 1 2 3 5
|
直接在A函数中用print导致函数可复用性较差,因为A函数返回None,其它函数无法获得函数生成的数列。要提高A函数的可复用性,需返回一个列表(list)
列子2:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
| def A(max): a,b,c = 0,0,1 L = [] while a < max: L.append(c) b,c = c, b+c a = a + 1 return L
结果: for a in A(5): 1 1 2 3 5
|
函数在运行中占用的内存随着参数增大而增大,如果要控制内存占用,不要用列表保存中间结果,而是通过iterable对象来迭代
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| for i in range(1000): #会导致生成一个1000个元素的列表 pass yield
def A(max): a,b,c = 0,0,1 while a < max: yield c # 打印C b,c = c,b + c a = a + 1
结果:for a in A(5): print(a) 1 1 2 3 5
|
yiled作用就是把一个函数变成生成器,带有yield函数不再是普通函数,解释会认为是一个生成器,调用A(5)不会执行A函数,而是返回一个生成器对象。
生成器的唤醒(next()函数和send()函数)
例子1:使用send()函数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
| def A(): i = 0 while i < 5: t = yield i print(t) i += 1
f = A() next(f) 0 f.send('111') 111 1 next(f) None 2 f.send('000') 000 3
|
使用send()函数可以在唤醒同时断点处传入一个附加数据执行到yield时,A函数作用暂时保存,返回i的值,t接收send发送的值
例子2:使用next函数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| f = A() next(f) 0 next(f) None 1 next(f) None 2 next(f) None 3 next(f) None 4 next(f) None #超出范围
|
例子3:使用__next__()函数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| f = A f.__next__() 0 f.__next__() None 1 f.__next__() None 2 f.__next__() None 3 f.__next__() None 4 f.__next__() #超出比较,报出异常 None
|