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

如何在typing.Generic泛型类中使用enforce_typing类型检查?

在泛型类中使用enforce_typing的解决方案

问题背景

enforce_typing的基础用法可正常实现类型校验:

from enforce_typing import enforce_types

@enforce_types
def bar(val : float) -> None:
    print(val)
    
bar(3.14) # 通过
bar('3.14') # TypeError: 期望参数'val'类型为'<class 'float'>',实际为'<class 'str'>'

但在泛型类中使用时,会抛出TypeError: isinstance() arg 2 must be a type or tuple of types错误,示例代码如下:

from enforce_typing import enforce_types
from typing import TypeVar, Generic
T = TypeVar('T')

class Foo(Generic[T]):
    @enforce_types
    def __init__(self, value: T) -> None:
        self.value = value

    @property
    def val(self) -> T:
        return self.value
    
foo = Foo[float](3.14)

问题原因

Python泛型类型在运行时会被类型擦除,enforce_typing装饰器校验时会调用isinstance()检查参数类型,但泛型变量T并非具体类型对象,导致isinstance()触发错误。

解决方法

方法1:让enforce_typing忽略泛型变量校验

使用enforce_typing的ignore_typevars=True参数,让装饰器跳过对泛型类型变量的校验:

from enforce_typing import enforce_types
from typing import TypeVar, Generic

T = TypeVar('T')

class Foo(Generic[T]):
    @enforce_types(ignore_typevars=True)
    def __init__(self, value: T) -> None:
        self.value = value

    @property
    @enforce_types(ignore_typevars=True)
    def val(self) -> T:
        return self.value
    
foo = Foo[float](3.14)  # 正常运行

注意:该方式会跳过泛型类型校验,若传入不符合T的类型(如Foo[float]("3.14")),不会触发报错。

方法2:手动实现运行时类型校验

若需要严格校验泛型的具体类型,可在实例化时捕获泛型绑定的具体类型,手动完成校验:

from enforce_typing import enforce_types
from typing import TypeVar, Generic

T = TypeVar('T')

class Foo(Generic[T]):
    def __init__(self, value: T) -> None:
        # 获取当前类绑定的泛型具体类型
        generic_base = self.__orig_bases__[0]
        target_type = generic_base.__args__[0]
        
        if not isinstance(value, target_type):
            raise TypeError(f"期望参数'value'类型为'{target_type}',实际为'{type(value)}'")
        self.value = value

    @property
    def val(self) -> T:
        return self.value
    
foo = Foo[float](3.14)  # 通过
foo = Foo[float]("3.14")  # 抛出TypeError: 期望参数'value'类型为'<class 'float'>',实际为'<class 'str'>'

内容的提问来源于stack exchange,提问作者J'e

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.15 06:35:28