【问题标题】:Executing Python code with a custom local dictionary使用自定义本地字典执行 Python 代码
【发布时间】:2013-04-01 10:28:46
【问题描述】:

作为this question I asked earlier 的后续行动,我正在尝试执行 Python 代码,就好像它在外部函数的上下文中一样。为此,我只需用def outer(): 包装一段代码,并进行一些简单的字符串处理以正确缩进内部代码。然后我编译它并通过执行co_consts列表中的第一个代码对象来执行编译后的内部代码。

例子:

mycode = """
print("Hey!")
"""

wrapped_code = 'def outer():\n    ' + '\n    '.join(mycode.strip().split('\n'))
compiled_code = compile(wrapped_code, '<str>', 'exec')
exec(compiled_code.co_consts[0], {}, {})

这会在外部函数的上下文中执行代码print("Hey")。 (如果有人想知道我为什么要这样做,它是我一直在研究的 C 扩展模块的一部分。)

问题:我遇到的一个问题是,如果我将代码包装在外部函数中,然后执行内部代码块,我似乎无法通过执行上下文的任何局部变量。

mycode = """
print(locals())
"""

wrapped_code = 'def outer():\n    ' + '\n    '.join(mycode.strip().split('\n'))
compiled_code = compile(wrapped_code, '<str>', 'exec')
exec(compiled_code.co_consts[0], {}, {"foo" : "bar"})

这个输出:

{}

请注意,我将包含{"foo" : "bar"} 的本地字典明确传递给exec,但是当它实际执行代码并打印locals() 时,它显示的是一个空字典。为什么Python没有使用我传递的局部变量字典?

【问题讨论】:

  • “如果有人想知道我为什么要这样做,那是我一直在研究的 C 扩展模块的一部分。” - 这并不能回答问题。我从未见过任何扩展模块可以做到这一点。
  • Include/code.hObjects/frameobject.c (PyFrame_New, 693-710)。
  • @eryksun,谢谢。你的评论解决了我的问题。我需要做的就是将函数代码对象中的co_flags 变量设置为0,这样它将使用我传递给它的本地字典,而不是为执行帧创建一个新的本地字典。

标签: python python-3.x


【解决方案1】:

您将一个函数作为第一个参数传递给 exec。一个函数将定义它自己的局部变量,这就是您要打印的局部变量。去掉包装(我看不出有什么用处),它就可以工作了。

【讨论】:

  • 有没有办法访问/操作函数本地字典?
  • @Channel72:从函数外部,没有。因为是本地的。你在叫错树,应该发布一个关于你实际上试图通过使用 exec() 解决的问题的问题。你几乎不需要使用 exec()。
猜你喜欢
  • 1970-01-01
  • 2019-11-07
  • 1970-01-01
  • 2019-06-03
  • 2015-07-11
  • 1970-01-01
  • 1970-01-01
  • 2021-10-30
  • 2019-04-07
相关资源
最近更新 更多