Функция imp.reload() в Python не работает?

#python #import

#python #импорт

Вопрос:

Вот краткий пример:

x.py:

 class x:
  var = 'from x.py'
  

y.py:

 class x:
  var = 'from y.py'
  

test.py

 import imp
def write_module(filename):
  fp = open('z.py', 'w')
  fp.write(open(filename).read())
  fp.close()

write_module('x.py')
import z
print(z.x.var) # Prints 'from x.py'
write_module('y.py')
imp.reload(z)
print(z.x.var) # Prints 'from x.py'
  

Я не уверен, почему оба оператора печати одинаковы. Как я могу заставить python использовать новое определение класса x после reload()?

Комментарии:

1. Вы также могли бы удалить .pyc файл, что заставит Python перекомпилировать модуль.

Ответ №1:

Это происходит потому, что даты создания файла ( z.py и его скомпилированного аналога z.pyc ) идентичны, поэтому Python считает, что файл не изменился, и не перекомпилирует его.

На самом деле, когда я пытался повторно использовать ваш код, он однажды сработал так, как ожидалось — вероятно, потому, что два файла были созданы по обе стороны от второго переключения системных часов.

 import imp
import time
def write_module(filename):
  fp = open('z.py', 'w')
  fp.write(open(filename).read())
  fp.close()

write_module('x.py')
import z
print(z.x.var) # Prints 'from x.py'
time.sleep(1)  # Wait one second
write_module('y.py')
imp.reload(z)
print(z.x.var) # Prints 'from y.py'
  

показывает ожидаемый результат.

Комментарии:

1. Другой способ обойти это, который позволяет избежать перехода в режим ожидания на секунду, — удалить кэшированный файл. Замените свою time.sleep(1) на os.remove(getattr(z, '__cached__', 'z.pyc')) import os вверху), и вы получите более быструю версию, которая все еще работает.