Python 3基类类型注释仅允许当前子类

时间:2020-02-26 14:55:11

标签: python python-3.x type-hinting

假设我有三个类,一个父类和两个子类:

class BaseModel:
    def merge(self, other):
        return self + other

class ChildA(BaseModel):
    pass

class ChildB(BaseModel):
    pass

父类具有一个方法,该方法采用当前类的另一个实例并返回当前类的新实例(超出此问题的范围)。

如何注释BaseModel.merge以将其限制为仅当前子类?

我可以做这样的事情:

def merge(self, other: BaseModel) -> BaseModel:
    return self + other

但这仍然允许我将ChildB的实例传递到ChildA中,因为两者都继承自BaseModel。我只希望在ChildA中允许ChildA,在ChildB中允许ChildB。在不重新实现每个子类的merge的情况下该怎么做?

1 个答案:

答案 0 :(得分:3)

用类型变量注释两个参数,以强制两个参数必须具有相同的类型。

from typing import TypeVar

B = TypeVar('B', bound='BaseModel')

class BaseModel:
    def __init__(self, x: int):
        self.x = x

    def __add__(self: B, other: B) -> B:
        return type(self)(self.x + other.x)

    def merge(self: B, other: B) -> B:
        return self + other

class ChildA(BaseModel):
    pass

class ChildB(BaseModel):
    pass


print(ChildA(3).merge(ChildA(4)).x)  # Valid; both arguments are ChildA      
print(ChildA(3).merge(ChildB(4)).x)  # Invalid; one ChildA and one ChildB