Python 2.6+ 和 3.* 有 next(),但 pre-2.6 只提供 object.next 方法。有没有办法在 pre-2.6 中获得 next() 样式;也许是一些“def next():”结构?
class Throw(object): pass
throw = Throw() # easy sentinel hack
def next(iterator, default=throw):
"""next(iterator[, default])
Return the next item from the iterator. If default is given
and the iterator is exhausted, it is returned instead of
raising StopIteration.
"""
try:
iternext = iterator.next.__call__
# this way an AttributeError while executing next() isn't hidden
# (2.6 does this too)
except AttributeError:
raise TypeError("%s object is not an iterator" % type(iterator).__name__)
try:
return iternext()
except StopIteration:
if default is throw:
raise
return default
(
throw = object()
也有效,但这在检查时会生成更好的文档,例如 help(next)
。None
不合适,因为您必须以不同的方式对待 next(it)
和 next(it, None)
。)
R。佩特似乎有一个很好的答案。额外提醒一下:如果您正在编写代码以在许多不同版本的 Python 上运行,您可以对定义进行条件化:
try:
next = next
except NameError:
def next():
# blah blah etc
这样你就可以在任何情况下定义
next
,但是你使用的是可用的内置实现。
我使用
next = next
这样我就可以把这个定义放在一个模块中,然后在我的代码的其他地方使用:
from backward import next
更简单的方法:
import operator
next = operator.methodcaller("next")
Ned 关于将它放在
try
块中的建议在这里也适用,但如果你要走那条路,一个小注意事项:在 Python 3 中,在非迭代器上调用 next()
会引发 TypeError
,而这个版本会提高一个AttributeError
。
编辑:没关系。正如 steveha 指出的那样,
operator.methodcaller()
仅在 2.6 中引入,这是一种耻辱。