Chinaunix首页 | 论坛 | 博客
  • 博客访问: 467424
  • 博文数量: 63
  • 博客积分: 1485
  • 博客等级: 上尉
  • 技术积分: 596
  • 用 户 组: 普通用户
  • 注册时间: 2010-02-21 14:49
文章分类

全部博文(63)

文章存档

2018年(8)

2017年(25)

2016年(10)

2012年(6)

2010年(14)

我的朋友

分类: Python/Ruby

2017-01-02 22:11:16

这一篇讲的比较详细:
这两篇也很好:
Python函数式编程指南(三):迭代器
Python函数式编程指南(四):生成器

生成器函数:
返回的是一个生成器(generator),接下来每次对他调用next,那么就会返回一个值,一直到抛出StopIteration为止。

好处:
生成器不会一次性生成所有元素,所以占用很少内存。( i**2 for i in range(3))
列表表达式,一次性生成所有元素,所以占用大量内存。[ i**2 for in range(3) ],不同之处,就是方括号/圆括号。所以还是写yield比较清楚!

一段小程序:

点击(此处)折叠或打开

  1. def gen01(N):
  2.     for i in range(N):
  3.         yield i ** 2

  4. def gen02(N):
  5.     return (i**2 for i in range(N))    # 生成器表达式

  6. a=gen01(4)                             # 将这一行替换成下一行,执行结果是一样的
  7. # a=gen02(4)                      

  8. print type(a),dir(a)
  9. print a.next(), next(a)                # a.next()  与  next(a)
  10. print list(a)                          # list(a) 执行完,再次运行就会抛出StopIteration

  11. try:
  12.     print a.next()
  13. except StopIteration:
  14.     print "--- out of scope ---"

  15. try:
  16.     print next(a)
  17. except StopIteration:
  18.     print "--- out of scope again ---"

  19. for item in gen01(5):
  20.     print ">>", item,
  21. print ""
  22. for item in gen02(5):
  23.     print ">>", item,
  24. print ""
  25. print "sum[0,1,3,4,5]: ", sum(gen02(5))            # 累加
输出:

点击(此处)折叠或打开

  1. ['__class__', '__delattr__', '__doc__', '__format__', '__getattribute__', '__hash__', '__init__', '__iter__', '__name__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', 'close', 'gi_code', 'gi_frame', 'gi_running', 'next', 'send', 'throw']
  2. 0 1
  3. [4, 9]
  4. --- out of scope ---
  5. --- out of scope again ---
  6. >> 0 >> 1 >> 4 >> 9 >> 16
  7. >> 0 >> 1 >> 4 >> 9 >> 16
  8. sum[0,1,3,4,5]: 30

下面这个也是开篇提到的那边文章中的例子,乍一看,晕;运行一遍,仍旧觉得很神奇,目前我也没猜测出内部是怎么实现的。。。

点击(此处)折叠或打开

  1. def index_words_02(text):
  2.     if text:
  3.         yield 0
  4.     for index, letter in enumerate(text, 1):
  5.         if letter == ' ':
  6.             yield index

  7. cc = index_words_02("hello good bye")
  8. print type(cc), next(cc), cc.next(), next(cc)
  9. try:
  10.     print next(cc)
  11. except StopIteration:
  12.     print "---- Out of range ----"
输出:

点击(此处)折叠或打开

  1. <type 'generator'> 0 6 11
  2. ---- Out of range ----



阅读(1560) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~