2017-09-16 44 views
1

任何人都可以给我一个关于此行为的建议吗?下面的代码罚款运行:Python AST节点不能在函数内执行

import ast 


node = ast.parse('def nsd(a, b):\n if b == 0: return a \n return nsd(b, a%b)\n\nprint nsd(18,15)') 
obj = compile(node, filename="<ast>", mode="exec") 
exec obj 

但是,当我做同样的一个函数内部:

import ast 


def foo(): 
    node = ast.parse('def nsd(a, b):\n if b == 0: return a \n return nsd(b, a%b)\n\nprint nsd(18,15)') 
    obj = compile(node, filename="<ast>", mode="exec") 
    exec obj 

foo() 

它提出了一个错误:

Traceback (most recent call last): 
    File "C:/Users/Vectoun/PycharmProjects/untitled3/test.py", line 9, in <module> 
    foo() 
    File "C:/Users/Vectoun/PycharmProjects/untitled3/test.py", line 7, in foo 
    exec obj 
    File "<ast>", line 5, in <module> 
    File "<ast>", line 3, in nsd 
NameError: global name 'nsd' is not defined 

我想能够运行这里面有一个函数。有谁知道如何解决这个问题?

回答

0

如果我没有弄错,这里的问题是,当使用exec时,你仍然受限于范围。

所以运行AST代码的方法之外将定义nsd全球方法,而内foo()运行AST代码将使nsdfoo的直接范围的成员,所以调用将在查找方法失败。

您可以通过先定义nsd作为一个全球性的解决这个问题:

import ast 


def foo(): 
    code = """global nsd 
def nsd(a, b): 
    if b == 0: 
     return a 
    return nsd(b, a%b) 
print nsd(18,15) 
    """ 
    node = ast.parse(code) 
    obj = compile(node, filename="<ast>", mode="exec") 
    exec obj 

foo() 
+0

感谢工作的解决方案! – vecta