En Python, una vez que he importado un módulo X en una sesión de intérprete usando import X
, y el módulo cambia en el exterior, puedo recargar el módulo con reload(X)
. Luego, los cambios estarán disponibles en mi sesión de intérprete.
Me pregunto si esto también es posible cuando importo un componente Y desde el módulo X usando from X import Y
.
La declaración reload Y
no funciona, ya que Y no es un módulo en sí mismo, sino solo un componente (en este caso una clase) dentro de un módulo.
¿Es posible volver a cargar componentes individuales de un módulo sin salir de la sesión de intérprete (o importar el módulo completo)?
EDITAR:
Para aclarar, la pregunta es sobre importar una clase o función Y desde un módulo X y recargar en un cambio, no un módulo Y de un paquete X.
fuente
... possible ... import a component Y from module X
" vs "question is ... importing a class or function X from a module Y
". Estoy agregando una edición a ese efecto.Respuestas:
Si Y es un módulo (y X un paquete)
reload(Y)
estará bien; de lo contrario, verá por qué las buenas guías de estilo de Python (como las de mi empleador) dicen que nunca importe nada excepto un módulo (esta es una de las muchas razones importantes - sin embargo, la gente todavía mantienen la importación de funciones y clases directamente, sin importar lo mucho que explicar que es no una idea buena ;-).fuente
import this
del indicador interactivo para ver el Zen de Python); y todas las razones por las que los espacios de nombres son una gran idea (pistas visuales locales inmediatas de que se está buscando el nombre, facilidad para burlarse / inyectarse en las pruebas, capacidad de recarga, capacidad de un módulo para cambiar de manera flexible al redefinir algunas entradas, predecibles y controlables comportamiento en la serialización y recuperación de sus datos [[p. ej., decapando y despegando]], y así sucesivamente, ¡¡¡un comentario SO apenas es lo suficientemente largo para hacer justicia a este rico y largo argumento !!! -)importlib
paquete.importlib.reload(Y)
docs.python.org/3.4/library/… ver también stackoverflow.com/questions/961162/…Responder
De mis pruebas, la respuesta marcada, que sugiere una simple
reload(X)
, no funciona.Por lo que puedo decir, la respuesta correcta es:
Prueba
Mi prueba fue la siguiente (Python 2.6.5 + bpython 0.9.5.2)
X.py:
bpython:
fuente
Foo
que tiene un__init__.py
que busca un submódulo ... Publicaré una respuesta como contraejemplo.fuente
En primer lugar, no debería utilizar la recarga en absoluto, si puede evitarlo. Pero supongamos que tiene sus razones (es decir, depurar dentro de IDLE).
Recargar la biblioteca no devolverá los nombres al espacio de nombres del módulo. Para hacer esto, simplemente reasigne las variables:
Puede hacer esto de otras formas. Puede automatizar el proceso buscando en el espacio de nombres local y reasignando todo lo que fuera del módulo en cuestión, pero creo que estamos siendo lo suficientemente malvados.
fuente
Si quieres hacer esto:
Haz esto en su lugar:
Ahora puede usar myobject de la misma manera que estaba planeando (sin las tediosas referencias ilegibles de mymodule en todas partes).
Si está trabajando de forma interactiva y desea volver a cargar myobject desde mymodule, ahora puede usar:
fuente
suponiendo que lo haya usado
from X import Y
, tiene dos opciones:o
algunas consideraciones:
A. si el alcance de la importación no abarca todo el módulo (p. Ej., Importar en una función), debe utilizar la segunda versión.
B. si Y se importa a X desde otro módulo (Z), debe recargar Z, luego recargar X y luego recargar su módulo, incluso recargar todos sus módulos (p. Ej., Usar
[ reload(mod) for mod in sys.modules.values() if type(mod) == type(sys) ]
) podría recargar X antes de recargar Z, y luego no refrescar el valor de Y.fuente
reload()
móduloX
,reload()
módulo de importaciónY
deX
.Tenga en cuenta que la recarga no cambiará los objetos ya creados enlazados en otros espacios de nombres (incluso si sigue la guía de estilo de Alex).
fuente
Si está trabajando en un entorno jupyter, y ya tiene
from module import function
puede utilizar la función de magia,autoreload
porLa introducción de
autoreload
en IPython se da aquí .fuente
Solo para dar seguimiento a las respuestas de AlexMartelli y Catskul , hay algunos casos realmente simples pero desagradables que parecen confundir
reload
, al menos en Python 2.Supongamos que tengo el siguiente árbol de fuentes:
con el siguiente contenido:
init.py:
bar.py:
Esto funciona bien sin usar
reload
:Pero intente recargar y no tiene ningún efecto o corrompe las cosas:
La única forma en que podía asegurarme de que
bar
se volviera a cargar el submódulo erareload(foo.bar)
; la única forma en que accedo a laQuux
clase recargada es acercarme y tomarla del submódulo recargado; pero elfoo
módulo en sí se mantuvo aferrado alQuux
objeto de clase original , presumiblemente porque usafrom bar import Bar, Quux
(en lugar deimport bar
seguido deQuux = bar.Quux
); además, laQuux
clase se desincronizó consigo misma, lo cual es simplemente extraño.fuente