美文网首页PYTHON基础
15.生成器generator

15.生成器generator

作者: Stone_説 | 来源:发表于2020-12-21 00:44 被阅读0次

目录:
1.生成器介绍
2.生成器举例
3.生成器应用

1.生成器介绍

生成器指的是生成器对象,可以由生成器表达式得到,也可以使用yield关键字得到一个生成器函数,调用这个函数得到一个生成器对象
生成器函数:

函数体中包含yield语句的函数,返回生成器对象
生成器对象,是一个可迭代对象,是一个迭代器
生成器对象,是延迟计算,惰性求值的

2.生成器举例

普通的函数调用fn(),函数会立即执行完毕,但是生成器函数可以使用next函数多次执行

>>> y = (i for i in range(5))
>>> print(type(y))
<class 'generator'>
>>> print(next(y))
0
...
>>> print(next(y))
4
>>> print(next(y))
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
StopIteration

生成器函数等价于生成器表达式,只不过生成器函数可以更加的复杂

>>> def inc():
...     for i in range(5):
...             yield i
>>> print(type(inc))
<class 'function'>
>>> print(type(inc()))
<class 'generator'>
>>> x = inc()
>>> print(type(x))
<class 'generator'>
>>> print(next(x))
0
>>> for y in x:
...     print(y,'*')
1 *
2 *
3 *
4 *
>>> for y in x:
...     print(y,'---')
>>>

在生成器函数中,使用多个yield语句,执行一次会暂停执行,把yield表达式的只返回
再次执行会执行到下一个yield语句
如果函数没有显示return语句,如果生成器函数执行到结尾,一样会抛出StopIteration异常

return语句依然可以终止函数运行,但return语句的返回值不能被获取到 return会导致无法继续获取下一个值,抛出StopIteration异常

>>> def gen():
...     print('line 1')
...     yield 1
...     print('line 2')
...     yield 2
...     print('line 3')
...     return 3
>>> next(gen())
line 1
1
>>> next(gen())
line 1
1
>>> g = gen()
>>> print(next(g))
line 1
1
>>> print(next(g))
line 2
2
>>> print(next(g))
line 3
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
StopIteration: 3
>>> print(next(g,'End'))
End

3.生成器应用

3.1无限循环

正确写法

>>> def counter():
...     i=0
...     while True:
...             i += 1
...             yield i
>>> def inc(c):
...     return next(c)
>>> c = counter()
>>> print(inc(c))
1
>>> print(inc(c))
2

错误写法

>>> def counter():
...     i = 0
...     while True:
...             i += 1
...             yield i
>>> def inc():
...     c = counter()
...     return next(c) 
>>> print(inc())
1
>>> print(inc())
1
3.2计数器

不使用匿名函数

>>> def inc():
...     def counter():
...             i = 0
...             while True:
...                     i += 1
...                     yield i
...     c = counter()
...     def _inc():
...             return next(c)
...     return _inc 
>>> foo = inc()
>>> print(foo())
1
>>> print(foo())
2

使用匿名函数

>>> def inc():
...     def counter():
...             i = 0
...             while True:
...                     i += 1
...                     yield i
...     c = counter()
...     return lambda:next(c)
>>> foo = inc()
>>> print(foo())
1
>>> print(foo())
2
3.3处理递归问题

原始代码

>>> def fib():
...     x = 0
...     y = 1
...     while True:
...             yield y
...             x,y=y,x+y
>>> foo=fib()
>>> for _ in range(5):
...     print(next(foo))
1
1
2
3
5
>>> for _ in range(3):
...     next(foo)
...     print(next(foo))
8
13
21
34
55
89

等效代码

>>> pre = 0
>>> cur = 1
>>> print(pre,cur,end=' ')
0 1 
>>> def fib1(n,pre=0,cur=1):
...     pre,cur=cur,pre+cur
...     print(cur,end = ' ')
...     if n == 2:
...             return 
...     fib1(n-1,pre,cur)
>>> fib1(13)
1 2 3 5 8 13 21 34 55 89 144 233

相关文章

网友评论

    本文标题:15.生成器generator

    本文链接:https://www.haomeiwen.com/subject/hircnktx.html