Rio*_*210 2 python import python-import
首先,stackoverflow 上有很多关于此问题的解决方案,但从我尝试过的解决方案来看,它们都不起作用。我正在远程机器(linux)上工作。我dir-2/module_2.py使用 ipython 解释器在文件中进行原型设计。另外,我试图避免使用绝对路径,因为该远程计算机中的绝对路径又长又难看,并且我希望我的代码在下载后在其他计算机上运行。
我的目录结构如下:
/project-dir/
-/dir-1/
-/__ init__.py
-/module_1.py
-/dir-2/
-/__ init__.py
-/module_2.py
-/module_3.py
Run Code Online (Sandbox Code Playgroud)
现在我想module_1从导入module_2。然而,这个 stackoverflow 帖子中提到的解决方案:使用链接
sys.path.append('../..')
import module_2
Run Code Online (Sandbox Code Playgroud)
不起作用。我收到错误:ModuleNotFoundError: No module named 'module_1'
此外,在 ipython 解释器中,会import .module_3抛出module_2错误:
Run Code Online (Sandbox Code Playgroud)import .module_3 ^ SyntaxError: invalid syntax
点运算符不是应该在同一目录中工作吗?总的来说,我对导入机制很困惑。非常感谢对最初问题的任何帮助!多谢!
如果您运行该module1.py文件并且想要导入,module2那么您需要类似的东西
sys.path.append("../dir-2")
Run Code Online (Sandbox Code Playgroud)
如果您使用sys.path.append("../.."),那么您添加到路径中的文件夹就是包含的文件夹,并且其中project-dir没有文件。module2.py
该语法import .module_3用于相对导入。如果您尝试执行module2.py并且它包含它,import .module_3则它不起作用,因为您正在使用module2.py脚本。要使用相对导入,您需要将module2.py和module_3.py视为模块。也就是说,其他一些文件导入 module2,而 module2 使用此语法从 module3 导入某些内容。
解决这两个问题的一种可能的解决方案是对项目进行属性组织并(可选,这是一个好主意)打包您的库(即,使您的代码“可安装”)。然后,一旦安装了您的库(在您正在工作的虚拟环境中),您就不需要hackysys.path解决方案。您将能够从任何文件夹导入您的库。
此外,不要将您的模块视为脚本(不要运行您的模块)。使用单独的 python 文件作为“可执行文件”(或入口点)并从那里导入您需要的所有内容。这样,module*.py文件中的相对导入将正常工作,并且您不会感到困惑。
可能的目录结构是
/project-dir/
- apps/
- main.py
- yourlib/
-/__ init__.py
-/dir-1/
-/__ init__.py
-/module_1.py
-/dir-2/
-/__ init__.py
-/module_2.py
-/module_3.py
Run Code Online (Sandbox Code Playgroud)
请注意,该yourlib文件夹及其子文件夹都包含一个__init__.py文件。使用这种结构,您只需运行main.py(名称不需要是main.py)。
如果您不想打包您的库,那么您可以添加sys.path.append("../")“main.py将project-dir/文件夹添加到路径中”。这样您的yourlib库将在 中“可导入” main.py。您可以执行类似的操作from yourlib import module_2,它将正常工作(并且module_2可以使用相对导入)。或者,您也可以直接放入文件夹main.py中project-dir/,根本不需要更改sys.path,因为project-dir/在这种情况下将是“工作目录”。
请注意,您还可以tests在其中有一个文件夹project-dir,并且要运行测试文件,您可以执行与运行main.py.
以前的解决方案已经解决了您的问题,但加倍努力会带来一些好处,例如依赖性管理,并且sys.path无论您身在何处都无需进行更改。有多种选项可以打包您的库,由于其简单性,我将展示使用诗歌的一种选项。
安装诗歌后,您可以在终端中运行以下命令来创建新项目
/project-dir/
- apps/
- main.py
- yourlib/
-/__ init__.py
-/dir-1/
-/__ init__.py
-/module_1.py
-/dir-2/
-/__ init__.py
-/module_2.py
-/module_3.py
Run Code Online (Sandbox Code Playgroud)
这将创建以下文件夹结构
mylib/
- README.rst
- mylib/
- __init__.py
- pyproject.toml
- tests
Run Code Online (Sandbox Code Playgroud)
然后,您可以根据需要添加该apps文件夹以及其中的子文件夹mylib/(每个子文件夹都有一个__init__.py文件)。
该pyproject.toml文件指定依赖项和项目元数据。您可以手动编辑它和/或使用诗歌来添加新的依赖项,例如
poetry new mylib
Run Code Online (Sandbox Code Playgroud)
例如,添加pandas为依赖项和开发依赖项。mypy之后,您可以运行
poetry build
Run Code Online (Sandbox Code Playgroud)
创建一个虚拟环境并在其中安装您的库。您可以激活虚拟环境,并且poetry shell可以从任何地方导入您的库。请注意,您可以更改库文件而无需poetry build再次运行。
最后,如果你想在 PyPi 中发布你的库让大家看到你可以使用
mylib/
- README.rst
- mylib/
- __init__.py
- pyproject.toml
- tests
Run Code Online (Sandbox Code Playgroud)
使用有组织的项目结构,为您执行的脚本提供明确的位置。特别是,如果您执行的脚本位于模块所在的文件夹之外,那就更好了。另外,不要将模块作为脚本运行(否则您无法使用相对导入)。
| 归档时间: |
|
| 查看次数: |
4130 次 |
| 最近记录: |