跨模块的前向引用[重复]

Posted

技术标签:

【中文标题】跨模块的前向引用[重复]【英文标题】:Forward references across modules [duplicate] 【发布时间】:2020-11-19 22:33:31 【问题描述】:

在 Python 类型中,循环依赖可以通过前向引用来解决:

class A:
    b: "B"

    def __init__(self, b: "B"):
        self.b = b


class B:
    a: A

    def __init__(self):
        self.a = A(self)

mypy 将成功地进行类型检查。

但是,如果我将 AB 拆分为单独的文件/模块:

a.py:

class A:
    b: "B"

    def __init__(self, b: "B"):
        self.b = b

b.py:

from .a import A


class B:
    a: A

    def __init__(self):
        self.a = A(self)

并使用 mypy 检查模块或包,它失败了:

$ mypy -p tt
tt/a.py:2: error: Name 'B' is not defined
tt/a.py:4: error: Name 'B' is not defined

除了将两者放在同一个文件中之外,还有其他方法可以解决这个问题吗?

(使用 Python 3.8.4 测试)

编辑:

关于循环导入的讨论,我添加了一个琐碎的__main__.py

from .b import B

B()

并使用python -m tt进行测试

【问题讨论】:

你必须导入它 @juanpa.arrivillaga 这将导致ImportError: cannot import name 'B' from partially initialized module 'tt.b' (most likely due to a circular import) 不要使用from module import name 使用import module 然后使用module.name 抱歉,我仍然收到循环导入错误消息。如果你确定这会奏效,你能提供一个最小的例子吗? 感谢您标记规范副本。奇怪的是,我如此专注于前向引用作为问题,我没想到要搜索循环导入。 【参考方案1】:

正如我最近suggested 你可以使用TYPE_CHECKING 变量:

# a.py
from typing import TYPE_CHECKING
if TYPE_CHECKING:
    from .b import B


class A:
    b: "B"

    def __init__(self, b: "B"):
        self.b = b
# b.py
from .a import A


class B:
    a: A

    def __init__(self):
        self.a = A(self)

【讨论】:

以上是关于跨模块的前向引用[重复]的主要内容,如果未能解决你的问题,请参考以下文章

如何在 CORBA IDL 中声明/使用对结构的前向引用?

Python中类型注释的自引用或前向引用[重复]

20210421-C++的前向声明

C++ 类的前向声明的用法

1-many 关系的前向访问通常是如何实现的?

spring之跨模块引用配置文件