首页 > 解决方案 > 对于 int __pow__ int 的 python 类型提示,如何修复 mypy 错误“Expression has type Any [misc]”?

问题描述

我有一个 python 函数,它使用带有两个 int 的 python __pow__ (**) 运算符,Mypy 告诉我表达式b ** e的类型为“Any”,其中 b 和 e 的类型为“int”。我试图将表达式转换为 int with int(b ** e),但仍然出现错误。如何正确键入提示此表达式?

另外,如果表达式b ** e确实返回类型“Any”,你能解释一下原因吗?

错误:

temp.py:7: error: Expression has type "Any"  [misc]
        power: Callable[[int, int], int] = lambda b, e: b ** e
                                                        ^

临时文件

from functools import reduce
from typing import Callable, Dict


def factorization_product(fact: Dict[int, int]) -> int:
    '''returns the product which has the prime factorization of fact'''
    power: Callable[[int, int], int] = lambda b, e: b ** e # error on expression "b ** e"
    product: Callable[[int, int], int] = lambda x, y: x * y
    return reduce(product, [power(b, e) for b, e in fact.items()], 1)

编辑:

我意识到我可以使用内置的 pow 和 operator.mul 而不是 lambda,但我仍然得到错误。

错误:

temp.py:8: error: Expression has type "Any"  [misc]
        return reduce(mul, [pow(b, e) for b, e in fact.items()], 1)
                            ^

修改后的 temp.py

from functools import reduce
from operator import mul
from typing import Dict


def factorization_product(fact: Dict[int, int]) -> int:
    '''returns the product which has the prime factorization of fact'''
    return reduce(mul, [pow(b, e) for b, e in fact.items()], 1)

标签: pythonpython-3.xmypypython-typing

解决方案


另外,如果表达式 b ** e 确实返回类型“Any”,你能解释一下为什么吗?

检查typeshed表明仅在对数字(类型)int平方的特殊情况下才返回an 。这是因为即使and是s,也可能是负数,在这种情况下,结果是 a 。由于结果可以是 a或,因此它看起来适用于一般情况。xLiteral[2]beintefloatfloatinttypeshedAny

我会说这是语言限制。理想情况下,我们可以@overload对 的所有非负整数使用x,但Literal仅支持特定值。

要在使用 的同时解决此问题--disallow-any-expr,请像这样使用typing.cast

power: Callable[[int, int], int] = lambda b, e: typing.cast(int, b ** e)

现在运行mypy --disallow-any-expr temp.py返回Success: no issues found in 1 source file

但在你盲目cast地添加. 您可能想在此处添加验证。例如,没有验证:eintfactorization_product

factorial_sized_lst = [0] * factorization_product({1: 2, 3: -4})

can't multiply sequence by non-int of type 'float'尽管mypy报告类型检查成功,但在运行时失败。


推荐阅读