可以隐式检查“零”或“空”的变量类型

2024-01-10

我有一个接收变量的函数x并检查它的“零”或“空”。

Using PEP-484 https://www.python.org/dev/peps/pep-0484/类型提示语法,我会使用什么类型提示?

我该如何检查它是否是明确的“boolable https://docs.python.org/3/reference/datamodel.html#object.__bool__“通过提供自定义__bool__ or __len__方法(所以结果bool(object) could be False),除了检查它是否实际上已经实现了__bool__ or __len__方法?

example:

def my_func(x: "what goes here?"):
    assert boolable(x)  # what to do in this line?
    if x:
        "some logic"
    else:
        "some other logic"

我不想接受任何物体;所有对象都有真值,但对于没有真值的类型__bool__ or __len__那总是True.


首先,由于评论似乎对此有点困惑,我想我应该首先陈述我的假设。我假设您正在尝试检查某些内容是否为 0 或空,或者是否为布尔值静态地-- 也就是说,您使用 PEP 484 类型注释代码并运行 mypy 等类型检查器来确定变量是否为零。

如果那是not你正在尝试做的事情,并且你正在尝试检查某些内容是否为零或为空或可布尔runtime(当实际运行你的代码时),你可以只使用 isinstance 检查 - 例如像这样的东西assert x == 0 or assert len(x) == 0 or assert hasattr(x, '__bool__') or hasattr(x, '__len__').


If you are尝试静态检查某些内容是否为零或空,不幸的是,无法使用 PEP 484 类型执行此操作。基本上,PEP 484 不允许您将“逻辑检查”与类型相关联——例如,您不能创建强制某些函数仅接受正整数的约束。

这在更复杂的类型系统中是可能的(参见依赖类型系统、细化类型系统等),但实现此类类型系统非常复杂,因此在不久的将来修改 PEP 484 以支持此类功能的可能性极小。

也就是说,有are至少 mypy 的一些计划添加对简单依赖类型的支持literals。例如,虽然我们可能无法轻易判断某个任意变量是否为零,但我们can告诉字面意思0是零。 (当尝试输入以下内容时,此功能特别有用open(...)例如,函数——它根据第二个参数的值返回不同的类型)。

有一些相关讨论在这里 https://github.com/python/mypy/issues/3062——也就是说,我不会屏住呼吸等待这一实施。这是一个相对复杂的功能。

目前,唯一真正的替代方案是退回到使用运行时检查或仅重组​​代码,这样您就不需要检查某些内容是否为零或为空。


但是,如果您想通过检查是否存在来检查某种类型是否“可布尔”__bool__ or __len__方法,您可以通过静态方式执行此操作使用协议 https://www.python.org/dev/peps/pep-0544/:

from typing import Union
from typing_extensions import Protocol

class HasBool(Protocol):
    def __bool__(self) -> bool: ...

class HasLen(Protocol):
    def __len__(self) -> int: ...

Boolable = Union[HasBool, HasLen]

def accepts_boolable(x: Boolable) -> None: pass

accepts_boolable(3)
accepts_boolable("asdf")

class NotBoolable: pass

accepts_boolable(NotBoolable())  # Mypy reports an error

您需要安装typing_extensions首先使用 pip 进行打包。协议尚未成为标准库的一部分,但预计将在不久的将来实现标准化。我也不确定 mypy 之外的其他类型检查器是否支持协议。

有关协议的更多文档 https://mypy.readthedocs.io/en/latest/protocols.html.

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

可以隐式检查“零”或“空”的变量类型 的相关文章

随机推荐