我有一个类似如下的模块结构:
.
└── testmodule
├── __init__.py
└── submodule
├── __init__.py
└── implementation.py
2 directories, 3 files
以下是每个文件的内容
# testmodule/__init__.py
import submodule
# testmodule/submodule/__init__.py
from implementation import *
# testmodule/submodule/implementation.py
class Car(object):
def __init__(self):
self.doors = 2
self.color = 'red'
为什么课程实施没有"重新加载"当我在下面的测试中使用reload()
时?
Python 2.7.12 (default, Oct 11 2016, 05:24:00)
[GCC 4.2.1 Compatible Apple LLVM 8.0.0 (clang-800.0.38)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> import testmodule
>>> car = testmodule.submodule.Car()
>>> car.doors
2
>>> # I edit the file and change self.doors = 2 to self.doors = 4
>>> reload(testmodule)
<module 'testmodule' from 'testmodule/__init__.pyc'>
>>> car = testmodule.submodule.Car()
>>> car.doors
2
>>> # no more edits made before the Python REPL is restarted
me@laptop # python
Python 2.7.12 (default, Oct 11 2016, 05:24:00)
[GCC 4.2.1 Compatible Apple LLVM 8.0.0 (clang-800.0.38)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> import testmodule
>>> car = testmodule.submodule.Car()
>>> car.doors
4
更新
根据@ wim的逻辑,我将不得不重新加载testmodule.submodule.implementation
,然后重新加载testmodule.submodule
以使这个&#34;工作&#34;,事实确实如此。见这些测试:
Python 2.7.12 (default, Oct 11 2016, 05:24:00)
[GCC 4.2.1 Compatible Apple LLVM 8.0.0 (clang-800.0.38)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> import testmodule
>>> c = testmodule.submodule.Car()
>>> c.doors
2
>>> # I edit the file and change self.doors = 2 to self.doors = 4
>>> reload(testmodule.submodule.implementation)
<module 'testmodule.submodule.implementation' from 'testmodule/submodule/implementation.py'>
>>> c = testmodule.submodule.Car()
>>> c.doors
2
>>> reload(testmodule.submodule)
<module 'testmodule.submodule' from 'testmodule/submodule/__init__.pyc'>
>>> c = testmodule.submodule.Car()
>>> c.doors
4
me@laptop # python
Python 2.7.12 (default, Oct 11 2016, 05:24:00)
[GCC 4.2.1 Compatible Apple LLVM 8.0.0 (clang-800.0.38)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> import testmodule
>>> c = testmodule.submodule.Car()
>>> c.doors
2
>>> # I edit the file and change self.doors = 2 to self.doors = 4
>>> reload(testmodule.submodule)
<module 'testmodule.submodule' from 'testmodule/submodule/__init__.pyc'>
>>> c = testmodule.submodule.Car()
>>> c.doors
2
>>> reload(testmodule.submodule.implementation)
<module 'testmodule.submodule.implementation' from 'testmodule/submodule/implementation.py'>
>>> c = testmodule.submodule.Car()
>>> c.doors
2
>>> reload(testmodule.submodule)
<module 'testmodule.submodule' from 'testmodule/submodule/__init__.pyc'>
>>> c = testmodule.submodule.Car()
>>> c.doors
4
答案 0 :(得分:4)
TL; DR表示重新加载的预期行为。
导入testmodule
实际上会将子包加载到sys.modules
:
>>> import testmodule
>>> [m for m in sys.modules if m.startswith('testmodule')]
['testmodule.submodule', 'testmodule.submodule.implementation', 'testmodule']
现在,当您重新加载testmodule
时,它将直接获取testmodule
实施中的更改 - 即testmodule/__init__.py
中更改的所有行。
但是,您没有更改那里的任何行,submodule
包含引用的testmodule
名称仍将指向旧的submodule
。
基本上,元回答是你高估了“重新加载”对事物的敏感程度。你可以实现一个挂钩到子包中的深度重载,但是很难做到正确,我建议你不要打扰。
如果你有兴趣,IPython会朝这个方向做一些尝试:
# Python 2
import __builtin__
from IPython.lib import deepreload
__builtin__.reload = deepreload.reload
(有关详细信息,请参阅IPython.lib.deepreload
。)