python迭代器简单理解 __iter__和__next__方法

在使用for语句的时候,相当于python内部把for后面的对象使用了iter()方法。

a = [1, 2, 3]
for i in a:
	do_something()

for i in iter(a):
	do_something()

iter()的返回是一个迭代对象,主要映射到了类里的__iter__()方法。
对于使用iter()方法的对象,返回值为对象中的__iter__()方法的返回值。
iter()方法返回的是一个实现了__next__()方法的对象,由该对象实现的__next__()方法来完成实际的迭代。

class Node:
	def __iter__(self):
		return iter([1, 2, 3])

if __name__ == "main":
	n = Node()
	for i in n:
		print(i)

结果为:

1
2
3

Iterable:有迭代能力的对象,一个类,实现了__iter__(),就认为有迭代能力,通常此函数必须返回一个实现了__next__()的对象,如果自己实现了,可以返回self(返回值不是必须的)
Iterator:迭代器,同时实现了__iter__()和__next__()的对象。(若某个自定义类只实现了__next__()而未实现__iter__()则会报错)
在调用iter()方法的时候(例如for循环时),生成了一个迭代对象,要求__iter__()返回一个实现了__next__()的对象,可通过next()方法访问这个对象的下一个元素。如果不添加StopIteration异常,会不断迭代,for循环会捕捉这个异常并停止迭代。

class MyIter:
    def __init__(self):
        self._start = 0

    def __iter__(self):
        return self

    def __next__(self):
        if self._start < 10:
            self._start += 1
            return self._start
        else:
            raise StopIteration


if __name__ == '__main__':
    a = MyIter()
    for i in a:
        print(i)

结果:

1
2
3
4
5
6
7
8
9
10

如果同时实现了__iter__()和__next__()方法,且__iter__()没有返回self,调用iter方法时会返回__iter__()返回的结果

class MyIter:
    def __init__(self):
        self._start = 0

    def __iter__(self):
        return iter([1, 2, 3])

    def __next__(self):
        if self._start < 10:
            self._start += 1
            return self._start
        else:
            raise StopIteration


if __name__ == '__main__':
    a = MyIter()
    for i in a:
        print(i)

结果:

1
2
3

调用iter()方法时,iter()仅会被调用一次,next()则会多调用多次。

具体体现:

class MyIter:
    def __init__(self):
        self._start = 0

    def __iter__(self):
        self._start += 8
        return self

    def __next__(self):
        if self._start < 10:
            self._start += 1
            return self._start
        else:
            raise StopIteration


if __name__ == '__main__':
    a = MyIter()
    for i in a:
        print(i)

结果:

9
10

迭代器的优点:

  • 如果采用列表的方式遍历,会将列表中所有内容载入内存;如果使用迭代器,只有调用了next()方法时才会返回对应的结果,可以节约内存。
  • 不依赖索引的读取方式。
    迭代器的缺点:
  • 只能往后取值,不能往前取值;不能指定某一个值。
  • 无法预测迭代器的长度。

不能指定某一个值体现于:

a = iter([1, 2, 3])
print(a[1])

Traceback (most recent call last):
  File "D:/Project/python_fundamental/iterator_try/main.py", line 23, in <module>
    print(a[1])
TypeError: 'list_iterator' object is not subscriptable
posted @ 2021-12-11 17:11  Ravenna  阅读(3915)  评论(0编辑  收藏  举报