You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何避免Foo类被识别为__main__.Foo?解决跨模块加法兼容问题

跨模块类相加的类型判断问题:__main__.Foo 与导入的 Foo 不匹配

我将Foo和Bar两个类分别放在foo.py和bar.py文件中以规范代码结构,两者均实现了__add__方法,期望两个类的__add__方法能够兼容Foo或Bar实例的相加操作。

但直接运行foo.py时,执行bar + foo(其中foo是Foo实例,bar是Bar实例)会抛出TypeError错误——Bar的__add__方法会将foo识别为__main__.Foo,而非导入的foo.Foo,导致类型检查不通过。

相关代码

foo.py

from typing import Union, Any

import bar as b

FooBar = Union['Foo', 'b.Bar']


class Foo:
    message: str

    def __init__(self, message: str) -> None:
        self.message = message

    def __add__(self, other: Any) -> 'Foo':
        if not isinstance(other, (Foo, b.Bar)):
            raise TypeError('can only add Foo and Bar')
        return Foo(' '.join((self.message, other.message)))


def test():
    foo = Foo('Jalim')
    bar = b.Bar('Rabei')
    foobar = foo + bar # works just fine
    print(foobar.message)
    barfoo = bar + foo # raises TypeError because it receives __main__.Foo
    print(barfoo.message)


if __name__ == '__main__':
    test()

bar.py

from typing import Union, Any

import foo as f

FooBar = Union['f.Foo', 'Bar']


class Bar:
    message: str

    def __init__(self, message: str) -> None:
        self.message = message

    def __add__(self, other: Any) -> 'Bar':
        if not isinstance(other, (f.Foo, Bar)):
            print(f'{type(other) = }')
            raise TypeError('can only add Foo and Bar')
        return Bar(''.join((self.message, other.message)))

诉求与尝试

我知道可以在其他文件中运行test(),但希望能够直接运行foo.py,同时尽可能避免Foo被识别为__main__.Foo。

起初我尝试使用类型别名FooBar替代(Foo, bar.Bar)元组,但由于FooBar实际存储的是ForwardRef而非具体类型,无法用于isinstance检查;而直接将Foo和Bar放入Union会引发循环依赖问题。

内容的提问来源于stack exchange,提问作者Renan Elfo

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.16 21:12:39