1.迭代器 Iterator
概念: 可以被next()
函数调用并不断返回下一个值的对象称为迭代器:Iterator
。
可以直接作用于for
循环的对象统称为可迭代对象:Iterable
判断是否是Iterable对象
>>> from collections.abc import Iterable
>>> isinstance([], Iterable)
True
>>> isinstance({}, Iterable)
True
>>> isinstance('abc', Iterable)
True
>>> isinstance((x for x in range(10)), Iterable)
True
>>> isinstance(100, Iterable)
False
判断是否是迭代器的方法:
>>> from collections.abc import Iterator
>>> isinstance((x for x in range(10)), Iterator)
True
>>> isinstance([], Iterator)
False
>>> isinstance({}, Iterator)
False
>>> isinstance('abc', Iterator)
False
说明:真正去构建迭代器的情况很少,大多数情况下在类定义中__getitem__方法使元素边的可迭代,其他的交给迭代器协议。
2.生成器 generator
概念:在Python中,这种一边循环一边计算的机制,称为生成器:generator。
创建一个generator:
(1)把一个列表生成式的[]
改成()
,就创建了一个generator
[ ] list
( ) generator
>>> L = [x * x for x in range(10)]
>>> L
[0, 1, 4, 9, 16, 25, 36, 49, 64, 81]
>>> g = (x * x for x in range(10))
>>> g
<generator object <genexpr> at 0x1022ef630>
-
使用next(g)获取下一个返回值
注意: generator保存的是算法,每次调用next(g)
,就计算出g
的下一个元素的值,直到计算到最后一个元素,没有更多的元素时,抛出StopIteration
的错误。 -
可以使用for循环迭代下一个元素
>>> g = (x * x for x in range(10))
>>> for n in g:
... print(n)
...
0
1
4
9
16
25
36
49
64
81
(2) 如果一个函数定义中包含yield
关键字,那么这个函数就不再是一个普通函数,而是一个generator函数,调用一个generator函数将返回一个generator.
def fib(max):
n, a, b = 0, 0, 1
while n < max:
yield b
a, b = b, a + b
n = n + 1
return 'done'
说明: generator函数和普通函数的执行流程不一样。普通函数是顺序执行,遇到return
语句或者最后一行函数语句就返回。而变成generator的函数,在每次调用next()
的时候执行,遇到yield
语句返回,再次执行时从上次返回的yield
语句处继续执行。
二者区别: 来源
1.迭代器是访问容器的一种方式,容器已经出现了(譬如列表转为迭代器,列表里的元素已经确定了),我们只是从已有元素拓印出一份副本,只为我们此次迭代使用。而生成器则是自己生成元素。
——也就是前者是从有到有的复制,后者是从无到有
2.在用法上生成器只需要简单函数写法,配合yield就能实现。而迭代器真正开发中很难使用到,我们可以把生成器看做python给我们提供的特殊接口实现的迭代器。
---------------------------------------------简单理解-----------------------------------
迭代:是一种操作,逐个从集合获取元素的过程即为迭代。
可迭代/可迭代对象Iterable:是一种特性,简单来说就是可以for循环的对象(列表、元组、字典、字符串等)。
1.迭代器Iterator:支持next()操作的对象,可以使用iter()生成迭代器。
特性:
- 从头开始,一个一个返回
- 不能提前知道迭代器的长度
- 当所有元素都返回后再用next()获取的时候报异常错误StopIteration。
注意: list
、dict
、str
虽然是Iterable
,却不是Iterator
。但是可以使用iter()把他们变为可迭代对象。
2.生成器generator:一种特殊的迭代器。
生成器形成方式:
- [ ] 变为 ( ) 例子:g = (x * x for x in range(10))
- 函数里带yield(记住程序执行位置)
两者区别
- 生成器是生成元素的,迭代器是访问集合元素的一种方式。
- 迭代器是一种支持next()操作的对象,迭代器输出生成器的内容。
- 迭代器对象表示一个数据流,可看作有序序列。不知道长度,但是可以通过next()获取下一个元素。