[英]import order for sys.path for regular and namespace packages
正如官方文档所说( 模块搜索路径):
当导入名为 spam 的模块时,解释器首先搜索具有该名称的内置模块。 如果没有找到,它会在变量 sys.path 给出的目录列表中搜索名为 spam.py 的文件。
它将在sys.path
中从第一个到最后一个搜索 package 。
但我遇到一个例子不符合这一点。
这是一个例子:
当我安装 flask 时:
>>> import flask
>>> flask.__path__
['/home/yixuan/.local/lib/python3.6/site-packages/flask']
如果我在我的自定义目录(即 /home/yixuan/temp)下创建一个目录flask
,那么我运行这个:
>>> import sys
>>> sys.path
['', '/usr/lib/python36.zip', '/usr/lib/python3.6', '/usr/lib/python3.6/lib-dynload', '/home/yixuan/.local/lib/python3.6/site-packages', '/usr/local/lib/python3.6/dist-packages', '/usr/lib/python3/dist-packages']
>>> sys.path.insert(0, '/home/yixuan/temp')
>>> sys.path
['/home/yixuan/temp', '', '/usr/lib/python36.zip', '/usr/lib/python3.6', '/usr/lib/python3.6/lib-dynload', '/home/yixuan/.local/lib/python3.6/site-packages', '/usr/local/lib/python3.6/dist-packages', '/usr/lib/python3/dist-packages']
>>> import flask
>>> flask.__path__
['/home/yixuan/.local/lib/python3.6/site-packages/flask']
(这是两个单独的口译会话!)
而且我不知道为什么 flask package 不是我的自定义 flask 目录。 在sys.path
中, /home/yixuan/.local/lib/python3.6/site-packages
放在/home/yixuan/temp
之后,根据我的理解,这不正常,不是吗? 如果是这样,什么原因会导致这种情况发生?
没有__init__.py
( flask/
) 文件的目录是命名空间 package,而不是常规的 package ( flask/__init__.py
) 或模块 ( flask.py
)。 虽然命名空间包按sys.path
的顺序记录,但仅在根本找不到常规 package 或模块时才使用它们。
PEP 420 -- 隐式命名空间包
...
规格
...
在为父路径中的每个目录寻找名为“foo”的模块或 package 时:
- 如果找到
<directory>/foo/__init__.py
,则导入并返回常规 package。- 如果没有,但找到
<directory>/foo.{py,pyc,so,pyd}
,则导入并返回一个模块。 扩展的确切列表因平台以及是否指定-> O
标志而异。 这里的列表具有代表性。- 如果没有,但
<directory>/foo
找到并且是一个目录,则记录它并继续扫描父路径中的下一个目录。- 否则,扫描将继续父路径中的下一个目录。
如果扫描完成但没有返回模块或 package,并且至少记录了一个目录,则创建命名空间 package。
...
请参阅有关导入的sys.path 文档。 Flask 现在是 python 3 安装的一部分。
当导入名为 spam 的模块时,解释器首先搜索具有该名称的内置模块。 如果没有找到,它会在变量 sys.path 给出的目录列表中搜索名为 spam.py 的文件。 sys.path 从这些位置初始化。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.