为什么在编组代码上调用exec的函数会给出关于全局变量的错误? [英] Why does my function that calls exec on marshalled code give an error about globals?
问题描述
在玩 当我像这样使用 When I run this script using 它给出了预期的输出. 但是,如果我像这样介绍 However, when if I introduce 它会打印出预期输出的开头,然后输出错误信息 it prints the beginning of the expected output and then errors out 为什么说未定义 为了理解,我尝试像这样使用 In order to understand, I tried using 并按预期显示 我还注意到,当我在反序列化代码对象上使用 I've also noticed that when I use 它给了我如预期的整个拆卸过程. it gives me the entire disassembly as expected. 我什至看过 python使用的一些代码进行编译,尽管我认为 I've even looked at some of the code that python uses for compiling and although I think 此脚本成功地练习了您的simple.py代码3次.这澄清了什么吗?还是我误会了你的问题? This script successfully exercises your simple.py code 3 times. Does this clarify anything? Or am I misunderstanding your question? 这篇关于为什么在编组代码上调用exec的函数会给出关于全局变量的错误?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!compile()
,元帅模块和
exec
运行此脚本时exec
like thiswith open('simple.py', 'r') as f:
code = f.read()
exec code
This is a simple script that should count to 3.
This is iteration number 1
This is iteration number 2
This is iteration number 3
Inside foo()...
compile()
,marshal.dump()
和marshal.load()
compile()
, marshal.dump()
, and marshal.load()
like thisimport marshal
def runme(file):
with open(file, "r") as f:
code = marshal.load(f)
exec code
with open("simple.py", "r") as f:
contents = f.read()
code = compile(contents, "simple.py", "exec")
with open("marshalled", "w") as f:
marshal.dump(code, f)
runme("marshalled")
This is a simple script that should count to 3.
This is iteration number 1
This is iteration number 2
This is iteration number 3
Traceback (most recent call last):
File "./exec_within_function.py", line 17, in <module>
runme("marshalled")
File "./exec_within_function.py", line 8, in runme
exec code
File "simple.py", line 15, in <module>
main()
File "simple.py", line 12, in main
foo()
NameError: global name 'foo' is not defined
foo
? dir()
dir()
like thisimport simple # imports simple.py
dir(simple)
foo
已定义.['__builtins__', '__doc__', '__file__', '__name__', '__package__', 'foo', 'main']
dis.dis()
时(通过marshal.load()
读取),我看到的唯一是LOAD_NAME
和CALL_FUNCTION
的main()
,但是当我像这样用import
做到dis.dis()
on the deserialized code object (read via marshal.load()
), the only thing I see is the LOAD_NAME
and CALL_FUNCTION
for main()
, but when I do it with import
like thisimport dis, sys
import simple
dis.dis(sys.modules["simple"])
import
使用某种查找表进行定义,但我不确定compile()
与导致这种行为的区别是什么.import
uses some sort of lookup table for definitions, I'm not sure what the difference is with compile()
that's causing this behavior.推荐答案
# from original example
with open('simple.py', 'r') as f:
code = f.read()
exec(code)
# compile and run again
a = compile(code, "simple_compiled_this_file_not_created", "exec")
exec(a)
# marshal and unmarshal
import marshal
f = open("./marshalfoo.bin", "wb")
marshal.dump(a,f)
f.close()
b = marshal.load(open("./marshalfoo.bin", "rb"))
exec(b)