【发布时间】:2021-08-09 01:25:22
【问题描述】:
我正在为一个在我看来非常基本和常见的问题而苦苦挣扎,经过数小时的互联网搜索后我找不到任何答案的事实告诉我,我一定是做错了什么......
我只是想找到一种优雅的方式来处理我的包的导入。
背景:
我的包裹结构如下:
mypackage/
__init__.py
model/
__init__.py
A.py
B.py
controllers/
__init__.py
A.py
B.py
# mypackage/model/A.py
class A:
def __init__(self):
print("This is A's model.")
# mypackage/model/B.py
from mypackage.model.A import A as AModel
class B:
def __init__(self):
self._a_model = AModel()
print("This is B's model.")
# mypackage/controllers/A.py
class A:
def __init__(self):
print("This is A's controller.")
# mypackage/controllers/B.py
from mypackage.controllers.A import A as AController
class B:
def __init__(self):
self._a = AController()
print("This is B's controller.")
问题:
有两件事真的让我对这个设计感到困扰。
首先:我想使用命名空间
我真的不喜欢写作
from mypackage.controllers.A import A as AController
...
self._a = AController()
感觉很麻烦而且不是很pythonic... 我更喜欢使用如下命名空间:
from mypackage import controllers
...
self._a = controllers.A.A()
但如果我尝试,我会得到AttributeError: module 'mypackage.controllers' has no attribute 'A'
第二:我真的不喜欢输入班级的文件名
我真的不喜欢写作
from mypackage.controllers.A import A as AController
我更喜欢:
from mypackage.controllers import A as AController
什么不起作用
将所有内容放在一个文件中
我知道我可以通过将所有控制器的类(A 和 B)定义放在一个文件 (controllers.py) 中来得到我想要的,并对模型做同样的事情......
我读过几次,将多个类定义放在一个文件中是 python 中很常见的事情......但对于大型单独的类,我不能。如果 A 和 B 有数百行并且彼此没有任何关系(除了作为控制器和模型),那么将它们的定义放在一个文件中是不可用的。
在 init.py 文件中使用导入
确实可以解决我所有的问题...
除了:
- 这会导致循环导入。 如您所见,我在 B 的模型中需要 A 的模型......因此,如果在我需要访问其中一个模型时导入所有模型,我就会陷入恶性循环。 ..
- 这似乎不是很pythonic。如果只是因为它强制用户加载每个模块。
我在这里……
我的推理有什么问题?
【问题讨论】:
-
注意:这里所说的“命名空间”并不是 Python 中“命名空间”术语下通常引用的内容。但它并没有改变任何问题,只是一个旁白。
-
您是否尝试将一些导入添加到控制器目录的 init.py 中。
from A import A?比你应该能够给我们from mypackage.controllers import A as AController。如果我没记错的话:-)
标签: python python-import python-packaging