使.next()与python 2和3兼容

时间:2016-08-03 21:42:56

标签: python python-2.7 iterator

我已经在python 2.7中编写了代码,我想让它兼容  Python 3.x.到目前为止,我已经尝试了futurizemodernize python包以及2to3,一切似乎都很好。

但是我坚持使用python 2.7&#39} .next()方法。我收到futurize2to3个软件包的警告,例如:

RefactoringTool: Line 34: Calls to builtin next() possibly shadowed by global binding

当我在python 3.x中运行实际代码时,它会给我这个警告:

AttributeError: 'itertools._grouper' object has no attribute 'next'

python 2.7中的相关代码如下:

with open('file.txt', 'rU') as f:
    l = f.readlines()[2:]
    up = (x[1] for x in groupby(l, lambda line: line[0] == ">"))
    for u in up:
        head = u.next()[1:].strip()
        q = "".join(s.strip() for s in u.next())
        # do something

1 个答案:

答案 0 :(得分:2)

请勿直接调用.next()方法。请改用迭代器上的next() function

for u in up:
    head = next(u)[1:].strip()
    q = "".join(s.strip() for s in next(u))

next()函数将在Python 2和3上调用正确的挂钩。

但是,您从futurize看到的错误消息表明您已在您的代码中的其他位置绑定了名称next

如果你有类似的话:

next = some_expression

def next(...):
    # some function

作为全局,然后你遮蔽内置的next()函数。将next的任何其他用法重命名为该模块中的全局,以避免出现问题。

例如,以下演示代码会抛出您看到的消息:

$ cat demo.py
def next(): pass
n = g.next()
$ bin/futurize demo.py
RefactoringTool: Skipping optional fixer: idioms
RefactoringTool: Skipping optional fixer: ws_comma
RefactoringTool: Refactored demo.py
--- demo.py (original)
+++ demo.py (refactored)
@@ -1,2 +1,2 @@
 def next(): pass
-n = g.next()
+n = g.__next__()
RefactoringTool: Files that need to be modified:
RefactoringTool: demo.py
RefactoringTool: Warnings/messages while refactoring:
RefactoringTool: ### In file demo.py ###
RefactoringTool: Line 1: Calls to builtin next() possibly shadowed by global binding
RefactoringTool: ### In file demo.py ###
RefactoringTool: Line 1: Calls to builtin next() possibly shadowed by global binding

请注意该工具如何使用g.__next__()代替g.next(),以避免将next()用作函数。

从该代码中删除next函数会导致:

$ cat demo.py
# def next(): pass
n = g.next()
$ bin/futurize demo.py
RefactoringTool: Skipping optional fixer: idioms
RefactoringTool: Skipping optional fixer: ws_comma
RefactoringTool: Refactored demo.py
--- demo.py (original)
+++ demo.py (refactored)
@@ -1,2 +1,2 @@
 # def next(): pass
-n = g.next()
+n = next(g)
RefactoringTool: Files that need to be modified:
RefactoringTool: demo.py