最近学习了python中的生成器、迭代器、可迭代对象的知识,现在回顾一下,巩固理解
先说一下列表生成式:
执行结果如下:
通过方括号加入里面的表达式,从而生成一个列表,在这里注意一下,列表生成时也可以加入函数:
结果如下:
计算了X的三次方,结果存放在列表中。
生成器:
生成器的两种方式:一种是通过小括号() 一种是通过yield关键字,这里yield相当于return,不同之处在于yield结束
后会保存此时函数的状态。
先看第一种方式:
结果:
从结果看出gene_a 是一个生成器对象。
生成器对象的特点:
1:在你用到数据的时候,会给你生成,从而节省内存空间
2:不能跳跃取值,即只能顺序的生成值,
3:生成器是可迭代对象(后面会讲到什么是可迭代对象)
来看代码:
结果:
从结果我们可以看出,可以通过生成器对象进行取值。取值的方式有两种:一种是通过__next__()这种内置方法,但是不推荐使用。python2中采用的是next()方法,python3中采用的是next()的内置方法,使用效果如下next(gene_a)。
第4次next会抛出异常,超过迭代的范围,停止迭代。
也可以同通过for来进行数据生成:
结果:
这里面for内部做了两件事:
1:执行next方法
2:处理stopIteration异常
第二种生成方式时通过yield关键字:
结果:
我们可以看到gene_b 是一个生成器对象。那func2就是一个生成器函数。在这里yield就相当于return,进行for遍历时,for内部会自动给我们执行next(gene_b)功能,将返回值赋值给i,所以第一个next会打印1,当执行第二次next时,会找到第一次yield结束时保存的断点信息继续执行。所以第二次会打印出2。
增加一个小知识点: 生成器对象还有一个方法为send(), send()方法和next()方法的功能差不多。只不过send()方法可以传递参数。传递的参数会赋值给yield返回值的变量。value = yield 1。这里需要注意:第一次send前如果没有next只能进行必须执行send(None)
至此:生成器的两种生成方式已经讲解完毕。
什么是可迭代对象?
对象内部具有__iter__()方法的都是可迭代对象,比如列表,元祖,字典,字符串等,生成器也是可迭代对象。
迭代器:
先记住一句话: 生成器都是迭代器,迭代器不一定是生成器
迭代器定义:满足迭代器协议,协议为:1 有iter()方法,2 有next()方法
iter() 返回一个迭代器对象
将生成器的时候,说了for内部做了两件事,但是在迭代器中for除了那两件事还有一个事要做。就是通过iter()方法生成迭代器对象。
等价于:
到此为止:生成器,迭代器,可迭代对象全部讲完了。