使用枚举键创建 TypedDict

Cha*_*lie 5 python enums type-hinting python-typing typeddict

我正在尝试创建一个TypedDict更好的代码完成功能,但遇到了问题。

我想要有一组固定的键(枚举)和值来根据键匹配特定的对象列表。

例如:

from enum import Enum


class OneObject:
    pass

class TwoObject:
    pass

class MyEnum(Enum):
    ONE: 1
    TWO: 2
Run Code Online (Sandbox Code Playgroud)

我希望有这样的东西:

from typing import TypedDict


class CustomDict(TypedDict):
    MyEnum.ONE: list[OneObject]
    MyEnum.TWO: list[TwoObject]

Run Code Online (Sandbox Code Playgroud)

然而,我得到了Non-self attribute could not be type hinted,但它并没有真正起作用。我有什么选择?

Dan*_*erg 3

这与PEP 589中规定的规范不兼容。让我引用一下:(强调我的)TypedDict

TypedDict 类型表示具有一组特定字符串键以及每个有效键的特定值类型的字典对象。

因此,使用任意枚举成员来定义TypedDict键是无效的。

虽然TypedDict还支持替代的函数定义语法,并且理论上您可以通过执行使枚举具有str 数据类型class MyEnum(str, Enum): ...,但您仍然可能无法TypedDict类型检查器理解的方式使用这些枚举成员定义 a 。

这是因为只有实际的字符串文字才被正式接受为键,如最终值和文字类型的使用部分中提到的。引用:(再次强调我的)

类型检查器仅支持实际的字符串文字,而不是最终名称或文字类型,用于在 TypedDict 类型定义中指定键。[...]这样做的动机是使类型声明独立,并简化类型检查器的实现。

换句话说,是否支持类似以下内容完全取决于任何给定的类型检查器:

from enum import Enum
from typing import TypedDict


class OneObject:
    pass


class TwoObject:
    pass


class MyEnum(str, Enum):
    ONE = "1"
    TWO = "2"


CustomDict = TypedDict(
    "CustomDict",
    {MyEnum.ONE: list[OneObject], MyEnum.TWO: list[TwoObject]}
)
Run Code Online (Sandbox Code Playgroud)

Mypy(当前)没有并给出输出:error: Invalid TypedDict() field name。(顺便说一下,我用Final变量作为键对其进行了测试,但这些也被拒绝了。)

因此,根据您的用例,您可能必须硬着头皮再次显式输入枚举/键名称,或者首先不使用枚举,正如@artem 在他的回答中所建议的那样。