【问题标题】:How does the eval() function change the dict?eval() 函数如何改变字典?
【发布时间】:2012-11-09 14:30:20
【问题描述】:

eval() 如何改变字典?这是一个例子:创建一个 dict -> print -> eval -> print

>>> a={'a':'a','b':'b'}
>>> print(a)
{'a': 'a', 'b': 'b'}
>>> eval('a == "a"',a)
True
>>> print(a)
{'a': 'a', '__builtins__': {'bytearray': <class 'bytearray'>, 'IndexError': <class 'IndexError'>, 'all': <built-in function all>, 'help': Type help() for interactive help, or help(object) for help about object., 'vars': <built-in function vars>, 'SyntaxError': <class 'SyntaxError'>, 'UnicodeDecodeError': <class 'UnicodeDecodeError'>, 'memoryview': <class 'memoryview'>, 'isinstance': <built-in function isinstance>, '__build_class__': <built-in function __build_class__>, 'copyright': Copyright (c) 2001-2012 Python Software Foundation.
All Rights Reserved.
...

【问题讨论】:

  • 显然,确实如此。也许问题应该改成“如何……”、“为什么……”之类的。

标签: python dictionary python-3.x eval


【解决方案1】:

eval() 的第二个参数是用于eval() 运行的表达式的全局变量。

在评估表达式时,python 所做的一件事是确保 python 内置函数可用于评估的表达式,并为此将__builtins__ 条目添加到该全局命名空间。

所以,是的,eval() 调用确实改变了您的字典,这是预期的正常行为。它甚至在函数的文档中这样说:

如果 globals 字典存在且缺少“__builtins__”,则在解析 expression 之前将当前全局变量复制到 globals 中。这意味着 表达式 通常对标准 __builtin__ 模块具有完全访问权限,并且会传播受限环境。

如果您想避免此更改,请为全局变量使用空的 dict,并改用 a 作为 locals 命名空间:

eval('a == "a"', {}, a)

【讨论】:

【解决方案2】:

答案在the doc

首先,eval 的第二个参数是global 字典。比,我们看到:

如果全局字典存在且缺少“__builtins__”,则 在解析表达式之前,将当前全局变量复制到全局变量中。

是的,您的字典会通过调用 eval 进行修改。

【讨论】:

  • @xielingyun 当然。复制您的 dict 并将其提供给 eval() 并丢弃它。
【解决方案3】:

是的。 eval() 的第二个参数是“全局”字典,它解释了您所看到的内容。

【讨论】:

    猜你喜欢
    • 2016-09-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-10-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多