当代码有语法错误时如何创建python symtable?

时间:2014-03-15 17:15:25

标签: python introspection

当没有语法错误时:

>>> symtable.symtable("guido = 1; rossum = 2", "code", "exec").get_symbols()
[<symbol 'rossum'>, <symbol 'guido'>]

当出现语法错误时:

>>> symtable.symtable("guido = 1; for", "code", "exec").get_symbols()
guido = 1; for
             ^
SyntaxError: invalid syntax

有没有办法让这个容错?换句话说,在第二个例子中,是否可以生成一个具有&#34; guido&#34;即使代码中的其他地方存在语法错误,也会出现符号?

我已经尝试过寻找能够将带有语法错误的python代码转换为编译代码的模块(例如,通过从中删除不良语句),但我无法找到任何内容。

1 个答案:

答案 0 :(得分:0)

在典型的系统中,解析器在评估语言的任何语义之前运行(例如通过AST)。因此,在将符号识别为符号之前很久就检测到语法错误。所以根本不可能有一个符号表,因为只有在整个代码被解析后才会创建

如果你想以某种方式“修复”代码,你仍然可以捕获SyntaxError,然后以某种方式更改代码以获得可解析的代码。对于上面的例子,像这样的东西可以工作 - 但我很确定它不适用于更复杂的东西,所以你必须扩展它。

def getSafeSymbols (code):
    while True:
        try:
            tbl = symtable.symtable(code, "code", "exec")
        except SyntaxError as e:
            index = min(e.offset, len(code)) - 1

            # keep decrementing index until whitespace or statement separator
            while index >= 0 and code[index] not in ' \t\n;':
                index -= 1

            code = code[:index].strip()
        else:
            return tbl.get_symbols()
>>> getSafeSymbols("guido = 1; rossum = 2")
[<symbol 'guido'>, <symbol 'rossum'>]
>>> getSafeSymbols("guido = 1; for")
[<symbol 'guido'>]
>>> getSafeSymbols("guido = foo; bar = baz")
[<symbol 'baz'>, <symbol 'foo'>, <symbol 'guido'>, <symbol 'bar'>]
>>> getSafeSymbols("guido = foo; bar = ")
[<symbol 'foo'>, <symbol 'guido'>, <symbol 'bar'>]