代码之家  ›  专栏  ›  技术社区  ›  Petr Petrov

Python:使用eval在字符串中执行代码

  •  3
  • Petr Petrov  · 技术社区  · 8 年前

    我有一个语法树

    Tree(if, [Tree(condition, [Token(VARIABLE, 'age'), Token(ACTION_OPERATOR, '>'), Token(SIGNED_NUMBER, '18')]), Tree(result, [Tree(if, [Tree(condition, [Token(VARIABLE, 'salary'), Token(ACTION_OPERATOR, '>'), Token(SIGNED_NUMBER, '100000')]), Tree(result, [Token(STRING, 'success')]), Tree(condition, [Token(VARIABLE, 'salary'), Token(ACTION_OPERATOR, '<'), Token(SIGNED_NUMBER, '50000')]), Tree(result, [Token(STRING, 'fail')]), Tree(else, [Token(STRING, 'get_more_info')])])]), Tree(else, [Token(STRING, 'fail')])])
    

    我将其转换为字符串:

    if age > 18:
        if salary > 100000:
            print('success')
        elif salary < 50000:
            print('fail')
        else: 
            print('get_more_info')
    else:
        print('fail')
    

    我声明变量:

    age = 20
    salary = 60000
    

    并尝试使用

    eval(code)
    

    并得到一个错误

    File "<string>", line 1
    if age > 18: 
     ^
    SyntaxError: invalid syntax
    
    2 回复  |  直到 8 年前
        1
  •  3
  •   Taku    8 年前

    你在寻找 exec 不 eval :

    code = """
    if age > 18:
        if salary > 100000:
            print('success')
        elif salary < 50000:
            print('fail')
        else: 
            print('get_more_info')
    else:
        print('fail')"""
    
    exec(code, {"age": 20, "salary": 60000})
    # out: get_more_info
    

    执行董事 获取代码字符串或代码对象。虽然 评估 接受表达式。


    或者,您可以始终评估(使用 评估 )对象编码依据 compiling 事先输入代码字符串:

    eval(compile(code, '<string>', 'exec'), {"age": 20, "salary": 60000})
    # out: get_more_info
    

    只是为了好玩,你 可以 使用 评估 对于语法树,无需编译代码,但代码必须有所不同:

    code = 'print(("success" if salary > 100000  else "fail" if salary < 50000 else "get_more_info") if age > 18 else "fail")'
    
    eval(code, {"age": 20, "salary": 60000})
    # out: get_more_info
    

    这利用了Python的 ternary 条件,从技术上讲,它仍然被视为一个表达式。

        2
  •  1
  •   user3483203    8 年前

    你弄糊涂了 eval() 具有 exec() 。

    评估() 用于表达式,例如 False==True :

    >>> eval('False==True')
    False
    

    exec() 用于动态执行代码:

    age = 10
    s = '''
    if age > 18:
        if salary > 100000:
            print('success')
        elif salary < 50000:
            print('fail')
        else: 
            print('get_more_info')
    else:
        print('fail')
    '''
    
    exec(s)
    

    输出:

    fail