如何使用相对导入在包内运行模块? [英] How to run a module inside a package, using relative imports?

查看:88
本文介绍了如何使用相对导入在包内运行模块?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

此问题特定于 PyDev. 包结构如下所示:

app
├── __init__.py
├── sub1
│   ├── __init__.py
│   └── mod1.py
└── sub2
    ├── __init__.py
    └── mod2.py

mod1.py 模块:

from __future__ import print_function

def f():
    print('It works!')

mod2.py 模块:

from __future__ import absolute_import
from ..sub1 import mod1

if __name__ == '__main__':
    mod1.f()

一切从 shell 运行得很好python -m app.sub2.mod2 命令打印:

It works!

正如预期的那样,一切都很好.(from __future__ import absolute_import 行似乎没有效果:我可以将其注释掉,一切仍然正常.)

as expected, all is fine. (The from __future__ import absolute_import line seems to have no effect: I can comment it out and everything still works just fine.)

如果我在 PyDev IDE 中单击 mod2 并尝试 Run As > Python Run,我得到

If I click on mod2 in the PyDev IDE and try to Run As > Python Run, I get

ValueError: Attempted relative import in non-package

这并不奇怪,因为 -m 开关默认没有打开.如果我编辑 mod2 的运行/调试设置: Arguments > VM Arguments 并在此处添加 -m-m 最有可能传递给 python 解释器,但现在我得到:

which is not surprising as the -m switch is not turned on by default. If I edit the Run/Debug settings for mod2: Arguments > VM Arguments and add -m here; the -m is most likely passed to the python interpreter but now I get:

/usr/bin/python: Import by filename is not supported.

from __future__ import absolute_import 行似乎没有效果;我是否将其注释掉并不重要;我使用的是 Python 2.7.

The from __future__ import absolute_import line seems to have no effect; it does not matter whether I comment it out or not; I am using Python 2.7.

我现在没有想法.

  • 在 PyDev 中,如何在使用相对进口?

  • In PyDev, how can I run a module inside a package that uses relative imports?

我应该如何更改设置一次(全局),以便每当我尝试在包内运行一个模块,PyDev 做正确的事吗?(也就是说,我不必为每个单独指定设置我希望运行的模块.)

How should I change the settings once (globally) such that whenever I try to run a module inside a package, PyDev does the right thing? (That is, I don't have to individually specify the settings for each module that I wish to run.)

开发者亲自确认在PyDev中目前还无法实现;我已经为它开了一张票.

The developer in person confirmed that it is not possible in PyDev yet; I have opened a ticket for it.

在包内运行模块,使用相对导入

更新:截至 2016 年 12 月 2 日,问题已解决,请参阅已接受的答案.

UPDATE: As of Dec 2, 2016, the issue is resolved, see the accepted answer.

推荐答案

PyDev 5.4.0 中,现在有一个使用 -m 标志运行的选项(它将通过其常规名称导入模块,而不是像以前那样__main__ 这样相对导入就可以在那里工作).

In PyDev 5.4.0, there's now an option to run using the -m flag (which will import the module through its regular name and not as it was __main__ so that relative imports will work there).

您可以在以下位置启用它:Preferences >PyDev >运行(即:这将为所有运行启用它——也许将来会有一个选项可以每次运行都启用它,但现在它为所有启动设置了全局).

You can enable it at: Preferences > PyDev > Run (i.e.: this will enable it for all runs -- maybe in the future there'll be an option to make it per run, but for now it's set globally for all launches).

原答案:

问题是您的主模块中有相对导入,PyDev 使用 python path/to/file_to_execute.py 而不是 python -m my.module 执行文件>.

The problem is that you have relative imports in your main module and PyDev executes the file with python path/to/file_to_execute.py instead of python -m my.module.

一个简单的修复是做一个单独的主模块,然后从该模块导入一个 main() 函数并运行它(尽管再次:它不能在模块中以 __main__ (发生这种情况是因为模块名为 __main__,因此无法解析相对导入,因为它实际上并未使用可用于解析相对导入的名称导入).

A simple fix is doing a separate main module which in turn imports a main() function from that module and runs it (although again: it can't have relative imports in the module executed as __main__ (this happens because the module is called __main__ and thus cannot resolve a relative import because it wasn't actually imported with a name which can be used to resolve the relative import).

另一个修复是更改启动配置以在 VM 参数中添加 '-m my.module'(转到运行 > 运行配置来执行此操作 - 但您必须这样做对于您要运行的每个主要模块,包括单元测试).

Another fix would be changing the launch configuration to add the '-m my.module' in the VM arguments (go to run > run configurations to do that -- but you have to do that for each main module you want to run, including unit-tests).

最后一个修复是更改 PyDev 本身(因此,请在 PyDev 跟踪器中为此创建一个票证:https://www.brainwy.com/tracker/PyDev/ -- 或提交拉取请求,这样可以更快地添加该功能;) )

And the last fix would be changing PyDev itself (so, please create a ticket for that in the PyDev tracker: https://www.brainwy.com/tracker/PyDev/ -- or submit a pull request, which would make adding that feature much faster ;) )

这篇关于如何使用相对导入在包内运行模块?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆