Scala开发者求助:如何在Python中定义交换dict类型参数的类型别名
解决Python中交换dict类型参数的泛型类型别名问题
在Scala里你可以直接定义交换Map类型参数的泛型类型别名,但Python的类型系统语法和Scala不同,直接写Tcid = dict[B,A]无法正确绑定类型参数的顺序,导致MyPy报错。
问题根源
你原来的代码中,Tcid = dict[B,A]只是把Tcid绑定到一个依赖全局TypeVar的类型,而非让Tcid自身成为一个可接收类型参数的泛型别名。当你写Tcid[int,str]时,类型检查器会把int赋值给第一个全局TypeVar(B),str赋值给A,最终Tcid[int,str]等价于dict[int,str],和你返回的dict[str,int]类型不匹配,所以MyPy报错。
解决方案
根据你的Python版本,有两种正确的写法:
1. Python 3.12+(推荐)
Python 3.12引入了泛型类型别名的原生语法,可以直接指定类型参数的顺序和映射关系:
from typing import TypeVar A = TypeVar('A') B = TypeVar('B') # 明确声明Tcid是带两个类型参数的别名,Tcid[X,Y] 等价于 dict[Y,X] type Tcid[A, B] = dict[B, A] def test() -> Tcid[int, str]: return {"asd": 1} # MyPy会认可,因为Tcid[int,str]对应dict[str,int]
2. Python 3.9~3.11
需要结合typing.TypeAlias和Generic来声明泛型别名:
from typing import TypeVar, TypeAlias, Generic, dict A = TypeVar('A') B = TypeVar('B') # 先声明Tcid是Generic[A,B]的别名,再绑定到dict[B,A] Tcid: TypeAlias = Generic[A, B] Tcid = dict[B, A] def test() -> Tcid[int, str]: return {"asd": 1}
这样定义后,Tcid[int,str]就会正确映射为dict[str,int],和你的返回值类型匹配,MyPy就不会再报错了。
内容的提问来源于stack exchange,提问作者caeus
相关产品推荐
相关产品推荐

