概述
生成器的一个特点是,它是延时的操作,可以在需要的时候产出结果,而不是立即产生结果。而且,生成器也是一个迭代器。生成器也是单向有序地遍历,所以它只能遍历一次。
两种方式来构造生成器:
1.生成器函数:和普通函数一致,只不过是把return替换为yield,yield类似于next()函数,使用一次产出一个结果。然而,yield产出的结果并不是像next()一样立即打印出来,而是自动挂起并暂停执行。当yield被调用的时候,返回一个生成器对象,这个对象支持迭代器接口。
比如:
>>> def generator(n):
for i in range(10):
yield i+1
>>> for i in generator(4):
print i,":",
1 : 2 : 3 : 4 : 5 : 6 : 7 : 8 : 9 : 10 :
yield所在的函数返回的生成器对象支持迭代器接口:
>>> g=generator(3)
>>> g.next()
1
>>> g.next()
2
>>> g.next()
3
>>> g.next()
4
…………
StopIteration
2.通过列表来提供生成器:
>>> b=[x+1 for x in range(5)]
>>> b
[1, 2, 3, 4, 5]
>>> for i in b:
print i,":",
1 : 2 : 3 : 4 : 5 :
yield后面可以带数值,生成器函数内可以使用send()函数,这样我们就可以忽略掉中间那些输出,指定插入我们想要输出的内容:
>>> def g(a):
print "hello"
b=yield a
print b
d=yield 'hi'
e=yield 1
print "end"
>>> c=g("world")
>>> c.next()
hello
'world'
>>> c.send('jack')
jack
'hi'
>>> c.next()
1
>>> c.next()
end
Traceback (most recent call last):
File "<pyshell#88>", line 1, in <module>
c.next()
StopIteration
send()中断next():
def g(x):
while 1:
val=yield x
if val is not None:
x=val
else:
x+=1
>>> d=g(3)
>>> print d.next()
3
>>> print d.next()
4
>>> print d.send(100)
100
>>> print d.next()
101
当我们需要中断生成器,可以定义一个函数,通过throw抛出GeneratorExit异常:
def close(self):
try:
self.throw(GeneratorExit)
except(GeneratorExit,StopIteration):
print 'that is all'
还是前面的例子
>>> c=g('world')
>>> c.next()
hello
'world'
>>> close(c)
that is all
假如再次使用next():
>>> c.next()
Traceback (most recent call last):
File "<pyshell#129>", line 1, in <module>
c.next()
StopIteration
总结一下生成器:
实际上生成器就是一个迭代器,支持迭代器接口,可以用next()函数;语法上和普通函数类似,只是把return换成yield(带yiled的函数会被视为一个生成器);每执行一次yield,都会挂起生成器状态,需要时可以从挂起时位置调用
生成器有什么优点?
可以简化代码,使得代码行数更少,而且更易理解。生成器函数每次调用yield,都会产生一次中断,返回一个当前迭代值,函数内调用了多少次yield就相当于中断了多少次。打个比喻,使用普通函数时好比一边拨花生壳吃花生米,重复这样的循环,使用生成器的时候好比是你把花生都拨完壳,然后你可以想要什么时候吃就什么时候吃你的花生米
举例,斐波那契数列实现:
(1): (2):
>>> def fa(max): >>> for n in fa(5): | >>> def fab(max): |
最后
以上就是心灵美手机为你收集整理的python中的生成器generator的全部内容,希望文章能够帮你解决python中的生成器generator所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复