__iter__返回迭代器对象本身的目的是什么?

时间:2015-09-09 19:32:18

标签: python python-3.x

我不明白为什么__iter__特殊方法只返回它被调用的对象(如果在迭代器上调用它)。它本质上只是一个标志,表明该对象是一个迭代器吗?

编辑:实际上,我发现“这需要允许容器和迭代器与forin语句一起使用。” https://docs.python.org/3/library/stdtypes.html#iterator.iter

好的,这就是我理解的方式:编写for循环时,可以指定循环的迭代或迭代器。但是Python最终需要循环的迭代器,因此无论它给出什么,它都会调用__iter__方法。如果它被赋予了一个可迭代的,__iter__方法将产生一个迭代器,如果给它一个迭代器,__iter__方法同样会产生一个迭代器(给定的原始对象)。

2 个答案:

答案 0 :(得分:2)

这取决于你称之为的对象。如果一个对象已经是迭代器,那么就不需要将它转换为迭代器的操作,因为它已经是一个。但是如果对象不是迭代器,而是 iterable ,则从对象构造迭代器。

一个很好的例子是列表对象:

>>> x = [1, 2, 3]
>>> iter(x) == x
False
>>> iter(x)
<list_iterator object at 0x7fccadc5feb8>
>>> x
[1, 2, 3]

列表是可迭代的,但它们本身不是迭代器。 list.__iter__的结果不是原始列表。

答案 1 :(得分:1)

Python中,当您尝试使用loops时,或尝试迭代任何对象,如下所示。

让我们试着理解list对象..

>>> l = [1, 2, 3] # Defined list l

如果我们迭代上面的列表..

>>> for i in l:
...     print i
... 
1
2
3

当您尝试iteration超过list l时,Python for循环检查l.__iter__()哪个实习生返回迭代器对象。

>>> for i in l.__iter__():
...     print i
... 
1
2
3

为了更好地理解这一点,让我们自定义list并创建一个新的列表类..

>>> class ListOverride(list):
...     def __iter__(self):
...         raise TypeError('Not iterable')
... 

我已经在ListOverride创建了inherited来自list的实习生list.__iter__并覆盖了TypeError方法以提升>>> ll = ListOverride([1, 2, 3]) >>> ll [1, 2, 3]

ListOverride

我已经使用list类创建了一个新列表,并且由于它的列表对象,它应该以与>>> for i in ll: ... print i ... Traceback (most recent call last): File "<stdin>", line 1, in <module> File "<stdin>", line 3, in __iter__ TypeError: Not iterable 相同的方式进行迭代。

iterate

如果我们尝试ListOverride超过ll对象NotIterable,我们最终会获得{{1}}例外...