python输出器_Python生成器

简单的生成器,生成器解析式:

1 #usr/bin/env python3

2 #-*- codign=utf-8 -*-

3

4 myGenerator = (x*x for x in range(10)) #简单的生成器

5 print(type(myGenerator)) #输出

6 print(dir(myGenerator)); #输出:['__class__', '__del__', '__delattr__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__iter__', '__le__', '__lt__', '__name__', '__ne__', '__new__', '__next__', '__qualname__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', 'close', 'gi_code', 'gi_frame', 'gi_running', 'gi_yieldfrom', 'send', 'throw']

dir()发现里面发现有迭代器中的__iter__()和__next__(),这说明myGenerator是迭代器,是迭代器就可以用for循环。

1 #既然有迭代器的属性就可以用next()循环读取

2 print("First number:", next(myGenerator)) #First number: 0

3 print("Second Number:", next(myGenerator)) #Second Number: 1

4

5 #循环读取余下的

6 for i inmyGenerator:7 print(i) #输出1-10的平方的结果

再看熟知的list:

1 myList = [x*x for x in range(10)]; #定义列表解析式

2 print(type(myList)) #输出:

3 print(dir(myList)) ##['__add__', '__class__', '__contains__', '__delattr__', '__delitem__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__getitem__', '__gt__', '__hash__', '__iadd__', '__imul__', '__init__', '__init_subclass__', '__iter__', '__le__', '__len__', '__lt__', '__mul__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__reversed__', '__rmul__', '__setattr__', '__setitem__', '__sizeof__', '__str__', '__subclasshook__', 'append', 'clear', 'copy', 'count', 'extend', 'index', 'insert', 'pop', 'remove', 'reverse', 'sort']

4

5 #print(next(myList)) #出错:TypeError: 'list' object is not an iterator,说明不可迭代

6 #第一次循环有输出

7 for i inmyList:8 print(i) #有输出

9 #第二次循环还是有输出

10 for j inmyList:11 print(j) #有输出

总结:

1,生成器在第一次循环的时候,将myGenerator里的值依次读取并打印,再次读取的,就发现没有任何结果了。迭代器所具有的特性。这与列表不同。

2,生成器解析在很多地方都可以替代列表解析,因为,它占用内存少。

3,代码优雅简洁。如下:

1 sum(i*i for i in range(10)) #生成器

2 sum([i*i for i in range(10)]) #列表解析

yield,真正的生成器利器。

1 defmyGenerator():2 yield03 yield 1

4 yield 2

5

6 myGenerator =myGenerator()7 print(myGenerator) #输出:

8 print(type(myGenerator)) #输出:

9 print(dir(myGenerator)) #输出有:__iter__()和__next__()说明是迭代器

10 print(next(myGenerator)) #输出0

11 print(next(myGenerator)) #输出1

12 print(next(myGenerator)) #输出2

13 print(next(myGenerator)) #读取完了,错误提示,发起StopIteration

也就是说,这个含有yeild关键词的函数myGenerator返回值是一个生成器类型的对象。而这个生成器就是迭代器。也可以把含有yeild语句的函数叫做生成器。是一种用普通函数语法定义的迭代器。上例函数解析:

myGenerator = myGenerator()。调用函数并把它赋值给变量myGenerator,除了返回生成器外什么都没有做,任何值都不会返回。

print(myGenerator)。打印一下对象,说明是生成器类型。

print(type(myGenerator))。查看类型。

print(dir(myGenerator))。还是查看。

print(next(myGenerator))。生成器开始执行,遇到第一个yeild语句,将值返回并暂停执行(有的称之为挂起)。

print(next(myGenerator))。再次调用next(),从上次暂停的位置开始,将值返回,并暂停。

print(next(myGenerator))。重复上面操作。

print(next(myGenerator))。重复上面操作。

执行过程:yeild除了作为生成器的标志之外,还有一个功能就是返回值。既然是返回值,那么在函数内部跟return有什么区别?

首先看return:

1 defcheckReturn():2 print "Begin......"

3 while n >0:4 print("Before return.")5 returnn6 n -= 1

7 print("After return.")8 a = checkReturn(3) #输出了函数体内的第一个和第二个print语句:Begin...... Before return.

9 print(a) #执行函数体内的return n 语句,输出3

上面的代码并没有执行函数体内return语句后面的语句,也就是函数体内遇到return后只执行return语句,return语句后面的代码都不执行。

再看yeild:

1 defcheckYeild(n):2 print("Begin to check yield.....")3 while n >0:4 print("Before yeild.")5 yieldn6 n -= 1

7 print("After yeild")8

9 b = checkYeild(3) #调用函数checkYeild,除了返回生成器什么都不做

10 print("First time to call:", next(b)) #遇到yeild,返回值,暂停。

11 print("Second time to call:", next(b)) #从上次暂停位置继续执行

12 print("Third time to call:", next(b)) #又遇到yeild,返回值,暂停。

13 print("Forth time to call:", next(b)) #第四次调用的时候,发现n已经不满足条件while n>0了,发起StopIteration

用生成器些斐波那契数列:

1 deffibs(fmax):2 '''

3 Generator for fibonacci sequence4 '''

5 n, a, b = 0, 0, 1

6 while n <7 yieldb8 a b n="n">

10

11 if __name__ == "__main__":12 fs = fibs(10)13 for i infs:14 print(i)

生成器yeild还有几个方法:send(),throw(),close()。以后再说。

7>
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值