如果一个对象没有__contains__
实现,in
会使用基本如下的默认值:
def default__contains__(self, element):
for thing in self:
if thing == element:
return True
return False
如果一个对象没有__iter__
实现,for
会使用默认值,基本上是这样工作的:
def default__iter__(self):
i = 0
try:
while True:
yield self[i]
i += 1
except IndexError:
pass
即使对象不打算成为序列,也会使用这些默认值.
您的1 in f
和5 in f
测试正在使用in
和for
的默认回退,从而导致观察到的行为.1 in f
立即找到1
,但你的__getitem__
永远不会返回5
,所以5 in f
永远运行.
(事实上,在Python的参考实现中,默认的__iter__
回退将索引存储在Py_ssize_t
类型的C级变量中,因此如果等待足够长的时间,该变量将达到最大值Python raises an OverflowError.如果你看到了这一点,你必须使用32位Python构建.计算机的存在时间还不足以让任何人在64位Python上实现这一点.)