python - 有没有办法用mypy覆盖python中继承的类属性类型?

我写了一个 defaultdict 子类,它可以调用 default_factory 并将键作为参数。

from collections import defaultdict
from typing import TypeVar, Any, Callable, Generic

K = TypeVar('K')


class keydefaultdict(defaultdict, Generic[K]):
    ''' Drop-in replacement for defaultdict accepting key as argument '''

    default_factory: Callable[[], Any] | Callable[[K], Any] | None

    def __missing__(self, key: K) -> Any:
        if self.default_factory is None:
            raise KeyError(key)
        else:
            try:
                ret = self[key] = self.default_factory(key)
            except TypeError:  # try no-key signature
                ret = self[key] = self.default_factory()
            # if failed, let the error propagate as usual

            return ret

mypy 提示 default_factory 类型提示:

incompatible type in assignment (expression has type "Callable[[], Any] | Callable[[K], Any] | None", base class "defaultdict" defined the type as "Optional[Callable[[], Any]]")

有什么方法可以覆盖类型吗? mypy 也在这行 self.default_factory(...) 上提示 - 参数太多(或参数太少)和实例化此字典的地方(不兼容类型) :

data = keydefaultdict(lambda key: [key])

Argument 1 to "keydefaultdict" has incompatible type "Callable[[Any], list[Any]]"; expected "Optional[Callable[[], Any]]"

最佳答案

这是有意为之的行为,因为您所描述的违反了 Liskov substitution principle .参见 the mypy documentation了解更多详情。

出于这个原因,使用 defaultdict 作为子类是个坏主意。但是,如果您真的想解决这个问题(不推荐),您可以使用# type: ignore[override],像这样:

default_factory: Callable[[], Any] | Callable[[K], Any] | None # type: ignore[override]

这在 the mypy documentation 中有更详细的描述。如果您需要更多信息。

https://stackoverflow.com/questions/70843273/

相关文章:

java - 如何对 Map> 进行排序?

python - 将列名传递给 Pandas read_csv() 函数

flutter - 如何修复此语法错误?不可为 null 的实例字段 'students' 必须初始

postgresql - GROUP BY 时前两个值的差异

python - 如何使用 pybind11 从 C++ 调用 python 函数?

react-native - 如何在 React Navigation 中使用图标代替原来的后退按钮

julia - JuMP 非线性优化约束被打破到 O(1e-9)

pine-script - 如何在版本 5 中使用多个指标 ()

npm - sh : hardhat: command not found when install

apache-spark - 由于执行者丢失导致洗牌阶段失败