IPython重新加载了其他模块?

时间:2018-07-09 16:32:37

标签: python python-3.x import ipython reload

我用自己的阴影测试了Python的内置字符串模块 名为“字符串”的模块,以测试模块的搜索路径行为。我的习惯 字符串脚本的内容只有print('string' * 2)。它是 位于当前目录中,如下面的代码所示。

Python 3.6.4 |Anaconda custom (64-bit)| (default, Jan 16 2018, 10:22:32) [MSC v.1900 64 bit (AMD64)]
Type 'copyright', 'credits' or 'license' for more information
IPython 6.2.1 -- An enhanced Interactive Python. Type '?' for help.

In [1]: %pwd
Out[1]: 'C:\\Users\\stephen'

In [2]: import string

In [3]: string
Out[3]: <module 'string' from 'C:\\ProgramData\\Anaconda3\\lib\\string.py'>

In [4]: import imp

In [5]: imp.reload(string)
stringstring
Out[5]: <module 'string' from 'C:\\Users\\stephen\\string.py'>

有关在IPython中重新加载的三个问题:

  1. 为什么重新加载会认为它实际导入的模块(本地string.py)已经导入?它只是文件的相同性吗 名字?
  2. 为什么重新加载导入的模块不同于已导入的模块?它是否跳过了对sys.modules词典的检查, 在原始导入过程中首先检查?
  3. 为什么reload / IPython / Python不知道它已经在这里拉出了一个快速的模块,而是将一个模块切换为另一个模块?

编辑:在来回尝试照顾Stack Overflow抱怨我的代码块的过程中,我无意间丢失了一些我想说的话。这是我能记住的: IPython在启动时将内置的字符串模块添加到sys.modules词典中(在sys.path之前搜索sys.modules),而常规Python交互式提示则不这样做。因此,与交互式提示相对于IPython,我得到了不同的行为。在交互式提示下,我总是得到本地的string.py,因为sys.path从当前目录开始进行模块搜索。因此,我对常规交互式(Anaconda)和IPython之间的区别了解很多。我列出的问题仍然让我感到困惑。

2 个答案:

答案 0 :(得分:0)

Tested on my Kernel

看起来您正在使用本地模块名称,该名称掩盖了应用程序所依赖的标准库或第三方程序包或模块的名称。 Python导入通常从sys.path设置中检查,该设置可能在Users \ stephen下设置。因此,当我们重新加载它时,它将选择第一个匹配项。希望对您有所帮助。

以供参考:https://python-notes.curiousefficiency.org/en/latest/python_concepts/import_traps.html

答案 1 :(得分:0)

reload被设置为 ,以重复查找为其重新加载的模块的源代码的过程,如果它找到的文件与原始导入文件的文件不同,则为应该使用新文件。毕竟,它需要处理移动模块或将常规模块更改为软件包或扩展模块的情况。

reload应该不是sys.modules并在发现某物时停止。如果这样做,它将不会重新加载!

最初的IPython内部导入未进行时,reload找到本地string.py文件的原因是因为自第一次导入以来,导入路径已更改。您以不会导致Python本身将工作目录放在模块搜索路径上的方式运行IPython,并且IPython在该配置下从标准库中导入了string模块。之后,IPython将工作目录放置在模块搜索路径本身上,模仿了常规的交互式Python,因此reload找到了本地string.py