Soy bastante nuevo en python, y he estado jugando con él por un tiempo. He estado jugando con la función integrada compile()
, junto con marshal
y el exec()
incorporado. He notado algunas cosas para las que parece que no puedo encontrar las respuestas. Considere el siguiente script:Python exec() de un objeto de código marshaled
#!/usr/bin/python
def foo():
print "Inside foo()..."
def main():
print "This is a simple script that should count to 10."
for i in range(0, 10):
print "This is iteration number", i
foo()
if __name__ == "__main__":
main()
Esto funciona bien cuando se ejecuta a través de algo como:
with open('simple.py', 'r') as f:
code = f.read()
exec code
Sin embargo, cuando se compila en un objeto de código a través de compile()
, serializado a través marshal.dump()
, guardar en un archivo y luego leer del archivo, deserializado a través de marshal.load()
, y ejecutar con exec()
, se equivoca con un NameError
que indica que el nombre global foo
no está definido.
He visto la salida dada por dir()
, y cuando yo import()
el código, puedo ver que tiene una definición para foo()
. También me he dado cuenta que yo uso con dis.dis()
en el objeto de código deserializado (leer a través de marshal.load()
), lo único que veo es la LOAD_NAME
y CALL_FUNCTION
para main()
(en lugar de hacer algo así como exec 'import %s' % modname
, y luego hacer dis.dis(sys.modules[modname])
, lo que le da todo el desmontaje como se esperaba).
¿Tengo la certeza de que hay algún tipo de tabla de búsqueda que import()
consulta para obtener estas direcciones? (Para el registro, marqué http://svn.python.org/projects/python/trunk/Lib/py_compile.py y las únicas diferencias que pude ver en el bytecode que se generó a través de py_compile.compile()
y el compile()
incluido fue el imp.get_magic()
, junto con la marca de tiempo de 32 bits). Si tal tabla existe, ¿hay una buena manera de consultarla?
Gracias!
cuando lo que se serializa a través de 'marshal.dump()'? el archivo de texto? – Claudiu
El objeto de código para ese script generado a través de 'compile()'. – user1633448
¿Qué quieres decir? Lo siguiente parece funcionar: con open ('simple.py', 'r') como f: code = f.read() con open ('simple.mash', 'w') como f: marshal.dump (código, f) con ('simple.mash', 'r') abierta como f: código = marshal.load (f) código exec – Dhara