我正在运行Python 2.5。
这是我的文件夹树:
ptdraft/
nib.py
simulations/
life/
life.py
(每个文件夹中都有__init__.py
,为了可读性已省略)
我应该如何从life
模块内部导入nib
模块?我希望能在不修改sys.path的情况下完成。
注意:正在运行的主模块位于ptdraft
文件夹中。
我正在运行Python 2.5。
这是我的文件夹树:
ptdraft/
nib.py
simulations/
life/
life.py
(每个文件夹中都有__init__.py
,为了可读性已省略)
我应该如何从life
模块内部导入nib
模块?我希望能在不修改sys.path的情况下完成。
注意:正在运行的主模块位于ptdraft
文件夹中。
%cd ..
import nib
即使没有__init__.py
文件也可以工作。
我在Linux和Windows 7上使用Anaconda 3进行了测试。
我发现以下方法可以从脚本的父目录导入包。在这个例子中,我想从app.db
包中导入env.py
中的函数。
.
└── my_application
└── alembic
└── env.py
└── app
├── __init__.py
└── db
import os
import sys
currentdir = os.path.dirname(os.path.realpath(__file__))
parentdir = os.path.dirname(currentdir)
sys.path.append(parentdir)
sys.path.append(os.path.dirname(os.path.dirname(os.path.realpath(__file__)))))
- juzzlinsys.path
通常是一个不好的想法。你需要一些方法(例如,PYTHONPATH
)让你的库对于其他代码可访问(否则它就不是真正的库);一直使用那个就好了! - Davis Herringfrom ...module_name import *
from ..module_name import *
另外,如果你想从父目录导入任何模块。那么,
from ...module_name.another_module import *
这样,如果你想要导入特定的方法,就可以使用这种方式。
sys.path.append
这样工作,我无法像这样导入我的库。这是我在开始谷歌搜索之前尝试做的事情 :) 好的,就是这个 ValueError: attempted relative import beyond top-level package
. - juzzlinfrom ... import name
不是指“从顶层导入name”,而是指“从父级的父级导入name”。我创建了一个嵌套的目录结构 a1/.../a9
,其中每个目录都包含一个 __init__.py
文件,使用 from . import next_dir
导入下一个目录。最后一个目录有一个文件,其中 from ....... import b
然后导入 a1/a2/a3/b
。(在 Python 3.8.2 中测试) - Cubi73两行最简解决方案
import os, sys
sys.path.insert(0, os.getcwd())
如果 parent 是你的工作目录,你想从 child 脚本中调用其他子模块。
你可以在任何脚本中从 parent 目录导入所有子模块并执行它,如下:
python child_module1/child_script.py
cd ptdraft
python -m simulations.life.life
你可以通过这种方式从 nib.py 导入任何东西,因为 ptdraft 目录在路径中。
对我而言,获取父目录的最短且我最喜欢的一行代码是:
sys.path.append(os.path.dirname(os.getcwd()))
或者:sys.path.insert(1, os.path.dirname(os.getcwd()))
os.getcwd()返回当前工作目录的名称,os.path.dirname(directory_name)返回传递的目录的目录名称。
实际上,在我看来,Python项目架构应该采用这样的方式:子目录中的任何模块都不会使用父目录中的任何模块。如果发生这样的情况,就值得重新考虑项目树。
另一种方法是将父目录添加到PYTHONPATH系统环境变量中。
import sys
sys.path.append('../')
我有一个专门针对Git存储库的解决方案。
首先,我使用了sys.path.append('..')
和类似的解决方案。如果您正在导入自己使用sys.path.append('..')
导入文件的文件,则会出现问题。
然后,我决定始终附加Git存储库的根目录。一行代码看起来像这样:
sys.path.append(git.Repo('.', search_parent_directories=True).working_tree_dir)
或者更详细地说:
import os
import sys
import git
def get_main_git_root(path):
main_repo_root_dir = git.Repo(path, search_parent_directories=True).working_tree_dir
return main_repo_root_dir
main_repo_root_dir = get_main_git_root('.')
sys.path.append(main_repo_root_dir)
import ptdraft.nib
或者
import nib
import nib
__init__.py
文件了。S.Lott: 我不知道该如何检查... - Ram Rachumsys.path
或者PYTHONPATH
的答案,查看 np8 的优秀回答。是的,它很长。是的,看起来需要很多工作。但这是唯一一个真正正确且干净地解决问题的答案。 - Aran-Fey