可迭代的与迭代器
可迭代的和迭代器是两个经常容易混淆的概念,这里说说这两个概念
iterable可迭代的">iterable可迭代的
任何调用iter函数可以获得一个迭代器的都是可迭代的。实现__iter__
方法,返回一个迭代器的对象是可迭代的;序列是可迭代的,因为它们实现了__getitem__
方法。
iter函数执行时会做如下操作
- 检查一个对象是否实现了
__iter__
, 从其中获得一个迭代器 - 如果没有实现
__iter__
方法,查看是否实现__getitem__
方法,从中创建一个迭代器,从0开始获取每一个元素。正是因为这一点,序列是可迭代的 - 如果都失败,抛出异常,对象是不可迭代的。
当需要自己实现的迭代对象时,需要实现__iter__
方法,因为从__getitem__
中创建迭代器是为了向后兼容,未来也许会被废弃。
iterator迭代器">iterator迭代器
任何实现无参next方法,每次返回一个元素,当没有更多元素时,返回StopIteration异常的对象,都是迭代器。迭代器也实现了iter方法,所以也是可迭代的。也就是迭代器提供了访问可迭代对象的接口,用户不需要知道其内部实现。
把可迭代对象变成一个迭代器是一个坏主意
迭代器模式的用途主要是
- 访问一个聚合对象的内容而无需暴露它的内部表示;
- 支持多次遍历聚合对象
- 为遍历不同的聚合结构提供一个统一的接口,即支持多态迭代。
为了支持多次遍历,调用iter函数时,需要返回一个全新的迭代器。如果可迭代器对象变成一个迭代器,那么它将返回原先的迭代器,它将只支持一次遍历。