好的,情景非常简单。我有这个文件结构:
.
├── interface.py
├── pkg
│ ├── __init__.py
│ ├── mod1.py
│ ├── mod2.py
这是我的条件:
- mod2需要导入mod1。
- interface.py和mod2都需要独立运行为主要脚本。 如果您愿意,可以将interface视为实际程序,将mod2视为包的内部测试器。
因此,在Python 2中,我只需在mod2.py内部执行import mod1
,然后python2 mod2.py
和python2 interface.py
将按预期工作。
然而,这就是我不太理解的部分,使用Python 3.5.2,如果我执行import mod1
; 然后我可以执行python3 mod2.py
,但python3 interface.py
抛出:ImportError: No module named 'mod1'
:(
因此,显然,Python 3建议使用import pkg.mod1
来避免与内置模块冲突。 好的,如果我这样做,我就可以执行python3 interface.py
; 但是然后我不能python3 mod2.py
,因为:ImportError: No module named 'pkg'
同样,如果我使用相对导入:
from . import mod1
然后python3 interface.py
就可以工作; 但是mod2.py会说SystemError: Parent module '' not loaded, cannot perform relative import
:( :(
我找到的唯一“解决方案”是向上移动一个文件夹,然后执行python -m pkg.mod2
,然后它就可以工作了。 但是我们必须将包前缀pkg
添加到该包中的其他模块的每个导入中吗? 更重要的是,要运行包内部的任何脚本,我是否必须记住向上移动一个文件夹并使用-m开关? 那是唯一的方法吗??
我很困惑。 这种情况在Python 2中非常简单明了,但在Python 3中看起来很笨拙。
更新:在此处上传了那些带有(上述“解决方案”)工作源代码的文件:https://gitlab.com/Akronix/test_python3_packages。 请注意,我仍然不喜欢它,而且比Python2解决方案难看得多。
我已经阅读过的相关SO问题:
- Python -- import the package in a module that is inside the same package
- How to do relative imports in Python?
- Absolute import module in same package
相关链接:
from pkg.mod1 import fun
,例如from .mod1 import fun
或from .import mod1
,这将避免提及包的名称。这两种方式都适用于Python 2和3。此处有一份好的阅读材料,关于相对导入的文章。 - init_js