检查对象是否为类型的正确方法是什么?泛型?

检查对象是否为类型的正确方法是什么?泛型?,第1张

检查对象是否为类型的正确方法是什么?泛型?

没有获得此信息的官方方法。该

typing
模块仍在大量开发中,并且没有公共API可言。(实际上,它可能永远不会有一个。)

我们所能做的就是查看模块的内部结构,并找到最简捷的方式来获取我们所需要的信息。而且由于该模块仍在开发中,其内部结构将发生变化。很多。


在python
3.5和3.6,泛型有一个

__origin__
是保持的参照原来的通用基类(即属性
List[int].__origin__
会一直
List
),但是这是在3.7改变。现在,找出某物是否通用的最简单方法可能是检查其
__parameters__
__args__
属性。

这是一组可用于检测泛型的函数:

import typingif hasattr(typing, '_GenericAlias'):    # python 3.7    def _is_generic(cls):        if isinstance(cls, typing._GenericAlias): return True        if isinstance(cls, typing._SpecialForm): return cls not in {typing.Any}        return False    def _is_base_generic(cls):        if isinstance(cls, typing._GenericAlias): if cls.__origin__ in {typing.Generic, typing._Protocol}:     return False if isinstance(cls, typing._VariadicGenericAlias):     return True return len(cls.__parameters__) > 0        if isinstance(cls, typing._SpecialForm): return cls._name in {'ClassVar', 'Union', 'Optional'}        return Falseelse:    # python <3.7    if hasattr(typing, '_Union'):        # python 3.6        def _is_generic(cls): if isinstance(cls, (typing.Genericmeta, typing._Union, typing._Optional, typing._ClassVar)):     return True return False        def _is_base_generic(cls): if isinstance(cls, (typing.Genericmeta, typing._Union)):     return cls.__args__ in {None, ()} if isinstance(cls, typing._Optional):     return True return False    else:        # python 3.5        def _is_generic(cls): if isinstance(cls, (typing.Genericmeta, typing.Unionmeta, typing.Optionalmeta, typing.Callablemeta, typing.Tuplemeta)):     return True return False        def _is_base_generic(cls): if isinstance(cls, typing.Genericmeta):     return all(isinstance(arg, typing.TypeVar) for arg in cls.__parameters__) if isinstance(cls, typing.Unionmeta):     return cls.__union_params__ is None if isinstance(cls, typing.Tuplemeta):     return cls.__tuple_params__ is None if isinstance(cls, typing.Callablemeta):     return cls.__args__ is None if isinstance(cls, typing.Optionalmeta):     return True return Falsedef is_generic(cls):    """    Detects any kind of generic, for example `List` or `List[int]`. This includes "special" types like    Union and Tuple - anything that's subscriptable, basically.    """    return _is_generic(cls)def is_base_generic(cls):    """    Detects generic base classes, for example `List` (but not `List[int]`)    """    return _is_base_generic(cls)def is_qualified_generic(cls):    """    Detects generics with arguments, for example `List[int]` (but not `List`)    """    return is_generic(cls) and not is_base_generic(cls)

所有这些功能均应在所有<= 3.7的python版本中起作用(包括使用

typing
模块反向移植的所有<3.5版本)。



欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/zaji/5601898.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-12-15
下一篇 2022-12-15

发表评论

登录后才能评论

评论列表(0条)

保存