13

有没有办法将给定的 Python 抽象语法树 (AST) 转换为源代码?

是一个很好的例子,说明如何使用 Python 的ast模块,特别是NodeTransformer. 我正在寻找一种将生成的 AST 转换回源代码的方法,以便可以直观地检查更改。

4

4 回答 4

10

Python 源代码树包含这样的实现:Demo/parser 目录中的unparse.py

编者按:随着ast.unparse()Python 3.9 的引入,unparse.py 已被移除,因此上面的链接已更新为指向 3.8。

于 2010-09-25T14:48:30.663 回答
4

我发现了一个不错的第三方库:astunparse它基于unparse.pyNed 在他的回答中提出的建议。例子:

import ast
import astunparse

code = '''
class C:
    def f(self, arg):
        return f'{arg}'

print(C().f("foo" + 'bar'))
'''

print(astunparse.unparse(ast.parse(code)))

运行产生

class C():

    def f(self, arg):
        return f'{arg}'
print(C().f(('foo' + 'bar')))

另一个简洁的功能是astunparse.dump漂亮地打印代码对象:

astunparse.dump(ast.parse(code))

输出:

Module(body=[
  ClassDef(
    name='C',
    bases=[],
    keywords=[],
    body=[FunctionDef(
      name='f',
      args=arguments(
        args=[
          arg(
            arg='self',
            annotation=None),
          arg(
            arg='arg',
            annotation=None)],
        vararg=None,
        kwonlyargs=[],
        kw_defaults=[],
        kwarg=None,
        defaults=[]),
      body=[Return(value=JoinedStr(values=[FormattedValue(
        value=Name(
          id='arg',
          ctx=Load()),
        conversion=-1,
        format_spec=None)]))],
      decorator_list=[],
      returns=None)],
    decorator_list=[]),
  Expr(value=Call(
    func=Name(
      id='print',
      ctx=Load()),
    args=[Call(
      func=Attribute(
        value=Call(
          func=Name(
            id='C',
            ctx=Load()),
          args=[],
          keywords=[]),
        attr='f',
        ctx=Load()),
      args=[BinOp(
        left=Str(s='foo'),
        op=Add(),
        right=Str(s='bar'))],
      keywords=[])],
    keywords=[]))])
于 2019-04-09T10:37:27.340 回答
4

从 Python 3.9 开始, ast 模块为此提供了一个unparse函数:

解析一个 ast.AST 对象并生成一个字符串,如果用 ast.parse() 解析回来,该代码将产生一个等效的 ast.AST 对象

于 2020-04-29T07:42:27.130 回答
1

看看http://pypi.python.org/pypi/sourcecodegen/0.6.14

于 2011-11-30T20:50:55.100 回答