有人可以向我解释__iter__()
和__next__()
函数如何处理索引吗?它们是基于0
还是基于1
?
我一直在玩它,但是我想知道Python在后端实际上在做什么。我尝试了下面的示例类:
>>> class my_class:
def __init__(self, *stuff):
self.__stuff = stuff
def __iter__(self):
self.__n = 0
return iter(self.__stuff)
def __next__(self):
if self.__n <= len(self.__stuff):
self.__n += 1
return self.__stuff(self.__n)
else:
raise StopIteration
>>> x = my_class(1, 2, 3, 4)
>>> for each in x:
print(each)
1
2
3
4
除非我弄错了,否则self.__n
使用的第一个__next__()
值应该是1
,应该会产生这个值,
>>> for each in x:
print(each)
2
3
4
我想念什么?如何知道从self.__stuff[0]
开始?
答案 0 :(得分:3)
调用for each in x:
时,它对类定义中的__next__()
不起作用,因此它以对象属性的1开始而不是2。
即使您想调用类似print(next(x))
的东西,它也会给您'TypeError:'tuple'object is not callable',因为self.__stuff(self.__n)
无效,因为self.__stuff
是一个元组self.__n
是一个整数。您只能致电tuple[int]
而不是tuple(int)
。
在代码提及后尝试以下代码,它将返回所需的输出,然后引发异常。
for each in x:
print(next(x))
结果:
2
3
4
raise StopIteration
答案 1 :(得分:2)
my_class
时,它首先调用__init__
,然后调用__iter__
,最后是__next__
。 __iter__
时,它return iter(self.__stuff)
然后结束,__next__
没有被调用。所以输出就是您所看到的。如果要调用__next__
,则可以这样更改代码(此处__next__
使用的self .__ n从1开始)
class my_class:
def __init__(self, *stuff):
self.__stuff = stuff
def __iter__(self):
self.__n = 0
print('__iter__ is called')
return self
def __next__(self):
print('__next__ is called')
if self.__n <= len(self.__stuff):
self.__n += 1
return self.__stuff(self.__n)
else:
raise StopIteration
提示:您可以使用print
来帮助您了解代码的功能,就像上面代码中的print
函数一样。
答案 2 :(得分:1)
cmd.exe
方法返回__iter__()
而不是iter(self.__stuff)
。这样,将遍历传递给self
的元组,而不是对象。