为什么Pycharm无法捕获类型错误?

时间:2018-06-20 18:39:18

标签: python pycharm

为什么Pycharm不能区分两种不同的Optional类型,我有点困惑。

请考虑以下代码。

def funcs(foo:Optional[str]=None):
    print(foo)

def funci(var:Optional[int]=None):
    funcs(var)

argi = 1
args = "something"
argn = None

funcs(argi)
funcs(args)
funcs(argn)

请注意,funcs内部的funci调用在将Optional [int]传递给正在寻找Optional [str]的函数中没有问题。 enter image description here

但是,如果我们删除Optional [str],检查树皮就会消失。 enter image description here

这是预期的行为吗?如果是,我该怎么办?

我的直觉说类型检查应该足够聪明,以区分Optional[str]Optional[int]之间的区别。我已经通读了PEP-526PEP-484,但无济于事。

1 个答案:

答案 0 :(得分:0)

如果您在当前版本的 PyCharm (2021.1) 中使用默认检查设置对此进行测试,则不会再发出删除 Optional 参数中的 funcs 类型提示后的第二个警告。 <块引用>

这是预期的行为吗?

是的,linter 是正确的。类型必须完全兼容,否则可能会出现潜在错误,linter 会正确警告您。在更严格的意义上,PyCharm 也应该在第一种情况下发出警告,因为 strint 之间可能不兼容。

让我们使用 Mypy static type checker,因为它的结果通常更准确。

以下内容:

def funcs(foo: Optional[str] = None):
    pass

def funci(var: Optional[int] = None):
    funcs(var)

会导致 Mypy 发出错误:

your_module.py: error: Argument 1 to "funcs" has incompatible type "Optional[int]"; expected "Optional[str]"
<块引用>

如果是,我该怎么办?

Python 使用 gradual typing 表示随着代码的运行,可以检查类型,从而逐渐提示正确性。

如果您明确检查类型:

def funci(var: Optional[int] = None):
    if var is None:
        funcs(var)

Mypy 静态类型检查器没有错误。如果您确定在调用 None 的行之前将值限制为 funcs(var),另一种方法是使用 cast