Python 迭代器和生成器
迭代器
在 Python 中,如果一个对象有 __iter__( ) 方法或 __getitem__( ) 方法,则这个对象是可迭代的(iterable)。其中 __iter__( ) 方法让对象可以用 for 循环遍历,__getitem__( ) 方法是让对象可以通过"实例名[index]"的方式访问实例中的元素。
可迭代对象:迭代器(包含生成器)、序列、字典和集合。
如果一个对象同时有 __iter__( ) 方法和 __next__( ) 方法,则这个对象是迭代器(iterator)。__next__( ) 方法是让对象可以通过 next(实例名) 访问下一个元素。
>>> from collections import Iterable,Iterator
>>> isinstance(object,Iterable) # 判断对象是否是可迭代的
>>> isinstance(object,Iterator) # 判断对象是否是迭代器
迭代器有两个基本的方法:iter() 和 next()。
>>> list = [1,2,3]
>>> it = iter(list) # 返回迭代器对象
>>> next(it)
1
>>> next(it)
2
>>> next(it)
3
>>> next(it)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
StopIteration # StopIteration 异常来结束迭代
生成器
在 Python 中,使用了 yield 的函数被称为生成器(generator)。调用生成器函数,会返回一个迭代器对象,只能用于迭代操作。每次遇到 yield 时,函数会暂停并保存当前所有的运行信息,返回 yield 产生的值。并在下一次执行 next() 方法时从当前位置继续运行。
>>> def f():
... n = 0
... while n < 3:
... yield n
... n += 1
...
>>> i = f()
>>> i
<generator object f at 0x0000000003F0EDE0>
>>> i.__next__()
0
>>> i.__next__()
1
>>> i.__next__()
2
>>> i.__next__()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
StopIteration
生成器表达式
另外一种创建生成器的方式是通过生成器表达式。
>>> n = (x for x in range(3))
>>> n
<generator object <genexpr> at 0x0000000003F0EDE0>
>>> n.__next__()
0
>>> n.__next__()
1
>>> n.__next__()
2
>>> n.__next__()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
StopIteration
推导式
列表推导式:[ expression for item in iterable if condition ]
>>> list = [i for i in range(5) if i % 2 == 0]
>>> list
[0, 2, 4]
字典推导式:{ key_expression:value_expression for expression in iterable }
>>> dict = {i:ord(i) for i in 'python'}
>>> dict
{'p': 112, 'y': 121, 't': 116, 'h': 104, 'o': 111, 'n': 110}
集合推导式:{ expression for item in iterable if condition }
>>> set = { i for i in [1,2,2,3,9] if i < 5 }
>>> set
{1, 2, 3}