红茶的个人站点

  • 首页
  • 专栏
  • 开发工具
  • 其它
  • 隐私政策
Awalon
Talk is cheap,show me the code.
  1. 首页
  2. 编程语言
  3. Python
  4. 正文

Python学习笔记番外:包的组织

2021年4月15日 967点热度 0人点赞 0条评论

Python学习笔记番外:包的组织

说实话,Python的代码引用和组织真是一塌糊涂,处处是坑。

我们在执行Python代码的时候,解释器仅仅会将当前工作目录加入sys.path,这就导致如果你的代码结构比较复杂,牵扯到多个子目录,那下面的代码互相引用就很麻烦了。

这还不是最最要命的,最最要命的是你有极大概率会遇到一个beyond top level error。

实例

我们先来看我的一个项目代码结构:

image-20210329181846208

项目目录下有三个层级平行的包carrier_pkg\land_pkg\takeoff_pkg。他们中的代码会进行相对引用,比如:

#carrier.py
from abc import ABCMeta, abstractmethod
from ..land_pkg.land_mode import LandMode
from ..takeoff_pkg.takeoff_mode import TakeoffMode
​
class Carrier(metaclass=ABCMeta):
    def __init__(self):
        self._takeoffMode = None
        self._landMode = None
        self._name=""

看似没毛病,carrier.py的上层目录是项目根目录,而且我们也创建了__init__.py,可以看作一个模块,然后我们通过根目录去引用land_pkg这个子模块,完全说的通。

但是我们一旦执行程序:

image-20210329182349146

这就是我所说的beyond top-level error。

我们再在debug窗口查看一下__package__变量:

image-20210329182512710

我们可以看到vikramaditya_carrier.py的所属包是carrier_pkg而非carrier_game_error.carrier_pkg,这就意味着它所属的顶级包是carrier_pkg而非carrier_game_error,所以你要是想通过它去引用项目根目录的其它包,那是做梦。

我不清楚Python为什么会这样设计,明明这种代码结构在PHP或者Java中相当常见,但Python就是表现出了这样古怪的行为。

解决方法

解决方法其实也不是很难,你的顶级包不会到根目录是吧,那我给你多套一层就是了:

image-20210329182941089

比如像上面这样,我们用一个包game_pkg代替项目根目录去包三个子包。

相应的,项目根目录下的test.py引用方式也要稍加修改:

from game_pkg.carrier_pkg.vikramaditya_carrier import VikramadityaCarrier
from game_pkg.carrier_pkg.queen_elizabeth_carrier import QueenElizabethCarrier
from game_pkg.carrier_pkg.nimitz_class_carrier import NimitzClassCarrier
from game_pkg.carrier_pkg.liao_ning_carrier import LiaoNingCarrier
lnCarrier = LiaoNingCarrier()
print(lnCarrier)

其它相对引用的部分不用做任何修改,我们再执行test.py:

image-20210329183151453

没有任何问题。

结论

如果你在使用相对引用的时候遇到了beyond top level error,那就多加一层包。

参考资料:

  • 彻底明白Python package和模块

  • Python 中的绝对导入和相对导入

  • Python beyond top level package error in relative import Solution

本作品采用 知识共享署名 4.0 国际许可协议 进行许可
标签: import Python 包
最后更新:2021年4月19日

魔芋红茶

加一点PHP,加一点Go,加一点Python......

点赞
< 上一篇
下一篇 >

文章评论

取消回复

*

code

COPYRIGHT © 2021 icexmoon.cn. ALL RIGHTS RESERVED.
本网站由提供CDN加速/云存储服务

Theme Kratos Made By Seaton Jiang

宁ICP备2021001508号

宁公网安备64040202000141号