我希望能够编写一个函数来检查字典是否与我的一致TypedDict,但是我无法获得正确的泛型类型。所以结果函数应该是这样的:
T = typing.Generic('T', bound=...) # This is `bound=...` something I want to find out
def check_typeddict(value: dict, to_type: typing.Type[T]) -> T:
# do some type checking
return typing.cast(T, value)
check_type(MyTypedDict, {'a': 5})
Run Code Online (Sandbox Code Playgroud)
像 usingTypedDict或dictfor the boundvalue 之类的东西不起作用,这根本不可能(还)还是我错过了其他东西?
对于以下示例,mypy返回错误:
错误:赋值中的类型不兼容(表达式类型为“A”,变量类型为“A1”)
from typing import Type
class A:
pass
class A1(A):
pass
class A2(A):
pass
def fun(A_type: Type[A]) -> A:
if A_type == A1:
return A1()
else:
return A2()
a1: A1 = fun(A1)
Run Code Online (Sandbox Code Playgroud)
理想情况下,我想做的是在以下签名中强制执行依赖项fun:
def fun(A_type: Type[A]) -> A_type
Run Code Online (Sandbox Code Playgroud)
这可能吗; 如果没有,推荐什么(注意:我希望它适用于尚未定义的子类A,所以我认为我不能使用overload装饰器)?我最好的选择只是使用cast吗?
以下文件:
from typing import List
class A:
def __init__(self, myStr):
self.chars: List[int] = list(myStr)
def toString(self):
return "".join(self.chars)
Run Code Online (Sandbox Code Playgroud)
typechecks (注意字符应该是 List[str] 而不是 List[int]): ? Python python3 -m mypy temp.py => Success: no issues found in 1 source file,但是下面我声明 toString 的返回类型的地方是:
from typing import List
class A:
def __init__(self, myStr):
self.chars: List[int] = list(myStr)
def toString(self) -> str:
return "".join(self.chars)
? Python python3 -m mypy temp.py
temp.py:9: error: Argument 1 to "join" of "str" has incompatible type "List[int]"; expected "Iterable[str]" …Run Code Online (Sandbox Code Playgroud) 我如何知道 tox 是否提供对特定工具的支持?
具体来说,我想知道为什么这个 tox.ini 部分适用于 flake8:
[flake8]
max-line-length = 120 # works like a charm
[testenv:flake8]
deps = flake8
commands = flake8 mypackage/
Run Code Online (Sandbox Code Playgroud)
而这个不适用于 mypy:
[mypy]
ignore-missing-imports = True # won't be taken into account
[testenv:mypy]
deps = mypy
commands = mypy mypackage/
Run Code Online (Sandbox Code Playgroud) 我的 python 代码中有这样的定义:
options = defaultdict(lambda: defaultdict(lambda: defaultdict(str)))
options['modem1']['ByCost'] = ...
options['modem1']['ByCarrier'] = ...
options['modem1']['BySimSignal'] = ...
options['modem1']['SwitchBackByTimer'] = ...
Run Code Online (Sandbox Code Playgroud)
在我的预提交/mypy 检查期间它失败了,因为消息如下:
Need type annotation for 'options'
Run Code Online (Sandbox Code Playgroud)
由于我没有看到这段代码有任何问题,那么有什么解决办法可以让它通过 mypy 检查这一行吗?
顺便说一句,除了在我的代码中设置之外,我正在寻找其他方法:
disable_error_codes with error code var-annotated
Run Code Online (Sandbox Code Playgroud)
多谢 !
杰克
Mypy 认为这对以下情况有效strict = true:
from typing import Dict, TypeVar
KeyType = TypeVar("KeyType")
ValueType = TypeVar("ValueType")
class InvertibleDict(Dict[KeyType, ValueType]):
def __inverse__(self) -> "InvertibleDict[ValueType, KeyType]":
new_instance: "InvertibleDict[ValueType, KeyType]" = self.__class__()
for key, value in self.items():
new_instance[value] = key
return new_instance
Run Code Online (Sandbox Code Playgroud)
但是,它不接受相同代码的以下更简洁版本,在最后一行说“关键字必须是字符串”:
from typing import Dict, TypeVar
KeyType = TypeVar("KeyType")
ValueType = TypeVar("ValueType")
class InvertibleDict(Dict[KeyType, ValueType]):
def __inverse__(self) -> "InvertibleDict[ValueType, KeyType]":
return self.__class__(**{value: key for key, value in self.items()})
Run Code Online (Sandbox Code Playgroud) 考虑以下最小示例:
from array import array
def foo(arr: array) -> None:
print(arr)
Run Code Online (Sandbox Code Playgroud)
我有一个带有参数的函数array。我的项目是静态类型的并使用mypy。Mypy 抱怨说:
Mypy: Missing type parameters for generic type "array".
你能帮我理解我应该如何输入提示参数吗?我似乎找不到有关该主题的文档。我不明白为什么 mypy 会认为这是一个通用类型。
为了澄清,根据我的理解,我使用的类型提示有效,但 mypy 仍然抱怨,因为它认为它是通用类型,并且想要“元素”的类型。我是否遗漏了什么,或者是 mypy 中的错误?
与此相关: 数组的类型提示是什么?
我最近收到了这个很好的答案,用于以下方面:
from typing import Union, cast
class Default:
"""Placeholder for default arguments."""
# ham[] is mutable. `None` has meaning (or is not preferred).
def spam(ham: Union[list[str], None, type[Default]] = Default):
if ham is Default:
ham = ['prosciutto', 'jamon']
#ham = cast(Union[list[str], None], ham)
#assert isinstance(ham, (list, type(None)))
if ham is None:
print('Eggs?')
else:
print(str(len(ham)) + ' ham(s).')
Run Code Online (Sandbox Code Playgroud)
mypy错误:
Failed (exit code: 1) (2655 ms)
main.py:17: error: Argument 1 to "len" has incompatible type "Union[List[str], Type[Default]]"; expected "Sized" …Run Code Online (Sandbox Code Playgroud) 我们的代码中有一个典型的数据转换模式:当值为 None 时,我们让它通过。例如,
def capitalize(value):
if value is None:
return None
return value.capitalize()
# usage example:
assert capitalize(None) is None
assert capitalize("hello world") == "Hello world"
Run Code Online (Sandbox Code Playgroud)
我可以这样注释它:
from typing import Optional
def capitalize(value: Optional[str]) -> Optional[str]:
if value is None:
return None
return value.capitalize()
Run Code Online (Sandbox Code Playgroud)
看起来不错,但是下面的代码
capitalize("Hello world").split()
Run Code Online (Sandbox Code Playgroud)
总是会让mypy抱怨。
error: Item "None" of "Optional[str]" has no attribute "split"
Run Code Online (Sandbox Code Playgroud)
有没有办法用类型注解来表达“None总是转换为None,str总是转换为str”的转换规则?
当在 Python 中编写不返回值的类型化函数(如其他语言中的“void”)时,最好和/或按惯例将其标记如下吗?
def say_hello(name: str) -> None
print(f"Hello, {name}.")
Run Code Online (Sandbox Code Playgroud)
或者,应该省略-> None?
def say_hello(name: str)
Run Code Online (Sandbox Code Playgroud)
我想我要问的是,-> None省略是否会导致返回类型未指定,或者无论如何都被认为是NoneType这样,因此没有必要?
mypy ×10
python ×10
python-3.x ×3
type-hinting ×3
arrays ×1
flake8 ×1
python-3.9 ×1
tox ×1
typechecking ×1
typing ×1