如何使这些相对导入在Python 3中有效?
我有一个这样的文件夹结构:
project/
__init__.py
foo/
__init.py__
first.py
second.py
third.py
plum.py
在 project/foo/__init__.py
文件里,我从 first.py
、second.py
和 third.py
导入了一些类,并把它们放进了 __all__
里。
在 first.py
里,有一个叫 WonderfulThing
的类,我想在 second.py
里使用它,并希望通过从 foo
导入 *
来实现。(这里不讨论我为什么想这么做,假设我有正当理由。)
在 second.py
中,我尝试了 from .foo import *
、from foo import *
和 from . import *
,但这些都没有成功导入 WonderfulThing
。我还试过 from ..foo import *
,结果出现了一个错误:“尝试进行超出顶层包的相对导入”。
我看过文档和PEP,但还是搞不清楚怎么才能让这个工作。任何帮助都会很感激。
补充说明/编辑:看起来我可能误解了 __all__
在包中的用法。我一直把它当作在模块中使用,
from .first import WonderfulThing
__all__ = [ "WonderfulThing" ]
但再看看文档似乎表明,__all__
可能只能在包中用来指定默认导入的模块名称;似乎没有办法包含不是模块的东西。
这样理解对吗?
一个非通配符的导入失败了(cannot import name WonderfulThing
)。尝试 from . import foo
也失败了,但 import foo
是可以的。不幸的是,dir(foo)
显示什么都没有。
1 个回答
编辑:我确实误解了问题:__all__
并不只是限制在模块上。
一个问题是你为什么想要使用相对导入。这里使用 from project.foo import *
是完全没问题的。其次,foo
上的 __all__
限制并不会阻止你使用 from project.foo.first import WonderfulThing
,或者直接使用 from .first import WonderfulThing
,这仍然是最好的方法。
如果你真的想导入很多东西,最好的办法可能是先用 from project import foo
,然后用 foo.WonderfulThing
来使用这些东西,而不是直接用 import *
然后直接使用 WonderfulThing
。
不过,针对你的直接问题,要从第二个文件 second.py
的 __init__
文件中导入,你可以这样做:
from . import WonderfulThing
或者
from . import *