python - 如何在python中向自定义dict子类添加类型注释?

标签 python

我有一个自定义 dict类似于 defaultdict 的子类但将丢失的 key 传递给 default_factory因此它可以生成适当的值。

class KeyDefaultDict(dict):
    __slots__ = ("default_factory",)

    def __init__(self, default_factory, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.default_factory = default_factory

    def __missing__(self, key):
        if self.default_factory is None:
            raise KeyError(key)
        ret = self[key] = self.default_factory(key)
        return ret

    def __repr__(self):
        return (
            f"{type(self).__name__}({repr(self.default_factory)}, {super().__repr__()})"
        )


d = KeyDefaultDict(int)
print(d["1"] + d["2"] + d["3"])  # out: 6
print(d)  # out: KeyDefaultDict(<class 'int'>, {'1': 1, '2': 2, '3': 3})

我想像我的项目的其余部分一样为这个类添加类型注释,但我找不到任何如何做到这一点的示例。
我看到 typing模块使用外部类来添加注释。例如,defaultdict将使用 typing.DefaultDict 进行注释其定义是class typing.DefaultDict(collections.defaultdict, MutableMapping[KT, VT]) .

所以它是一个子类 defaultdict 的外部类和通用 typing.MutableMapping .
但是,我认为他们这样做可能是因为他们不想更改原来的collections.defaultdict。 .我找到了 Generic 的子类示例和 Mapping但不是从 dict 等其他东西继承的类.

问题是:如何为此类添加类型注释以使其成为泛型类?
我是否需要扩展其他东西或为注释创建一个外部类?

我正在使用 python 3.7.5,我更喜欢直接从 dict 继承因此,出于性能原因,我不必实现所需的方法。

提前致谢。

最佳答案

我很晚了,但我刚刚在我自己的代码库中工作。
基本上,您需要使用输入 Mapping generic
这是 dict 使用的通用类型,因此您可以定义其他类型,例如 MyDict[str, int] .
对于我的用例,我想要一个特殊的字典,它可以干净地格式化自己以进行日志记录,但我会一直使用它
有各种类型,所以它需要打字支持。
如何:

import typing

# these are generic type vars to tell mapping to accept any type vars when creating a type
_KT = typing.TypeVar("_KT") #  key type
_VT = typing.TypeVar("_VT") #  value type


# `typing.Mapping` requires you to implement certain functions like __getitem__
# I didn't want to do that, so I just subclassed dict.
# Note: The type you're subclassing needs to come BEFORE 
# the `typing` subclass or the dict won't work.
# I had a test fail where my debugger showed that the dict had the items,
# but it wouldn't actually allow access to them

class MyDict(dict, typing.Mapping[_KT, _VT]):
    """My custom dict that logs a special way"""
    def __str__(self):
        # This function isn't necessary for your use-case, just including as example code
        return clean_string_helper_func(
            super(MyDict, self).__str__()
        )

# Now define the key, value typings of your subclassed dict
RequestDict = MyDict[str, typing.Tuple[str, str]]
ModelDict = MyDict[str, typing.Any]
现在使用您的子类字典的自定义类型:
from my_project.custom_typing import RequestDict #  Import your custom type

request = RequestDict()
request["test"] = ("sierra", "117")

print(request)
将输出为 { "test": ("sierra", "117") }

关于python - 如何在python中向自定义dict子类添加类型注释?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59427687/

相关文章:

python - 'input' 是 print() 的无效关键字参数

python - 有可用的 python 镜像吗?

python - 使用 python 将 xml 附加到 xml。我有两个需要合并的 xml 文件。所以无论如何我可以合并这两个文件

Python 文件 I/O : invalid syntax?

python - Image in Image with cvMatchTemplate - 但是怎么做呢?

python - 在 Python 中获取总物理内存

python - 有多少种方法可以将元素添加到列表中,哪种方法最快?

python - 使用反汇编器调试Python错误

python - 通过python控制links2

python - Pycharm调试Django项目(Dev分支)的问题