为什么ast.literal_eval()似乎忽略声明的变量?

时间:2014-03-06 20:37:52

标签: python dictionary eval

我听说ast.literal_eval比eval()更安全,但在更改我的代码时,我收到'格式错误的字符串/节点'错误。

例如:

bar = False
incorrect = {"foo":bar}
correct = {"foo":"bar"}

ast.literal_eval(incorrect) 

返回错误,但

ast.literal_eval(correct) 

返回预期的{“foo”:“bar”}

为什么第一次评估没有返回{“foo”:False}

2 个答案:

答案 0 :(得分:4)

因为它并不意味着那样做。来自文档:

  

安全地评估表达式节点或Unicode或Latin-1编码   包含Python表达式的字符串。提供的字符串或节点可以   只包含以下Python文字结构:字符串,   数字,元组,列表,dicts,布尔值和无。

ast.literal_evaleval用于将python代码的字符串表示形式转换为...有效的python代码。

这不起作用:

>>> ast.literal_eval({"foo": "bar"})
Traceback (most recent call last):
  File "<input>", line 1, in <module>
  File "/usr/lib/python2.7/ast.py", line 80, in literal_eval
    return _convert(node_or_string)
  File "/usr/lib/python2.7/ast.py", line 79, in _convert
    raise ValueError('malformed string')
ValueError: malformed string <-- Telltale right here.

那是因为你已经有一个有效的python结构,你试图评估它。

如果你在整个事情上加上引号,它会创建一个字典:

>>> ast.literal_eval('{"foo": "bar"}')
{'foo': 'bar'}

答案 1 :(得分:1)

来自documentation  在ast.literal_eval:

  

安全地评估表达式节点或包含Python表达式的Unicode或Latin-1编码字符串。提供的字符串或节点可能只包含以下Python文字结构:字符串,数字,元组,列表,dicts,布尔值和None。

     

这可用于安全地评估包含来自不受信任来源的Python表达式的字符串,而无需自己解析值。

bar确实是False,但不是 literal literal_eval看不到变量。它只适用于文字。