PyCharm 中类型提示 dict.items() 时的奇怪行为
Posted
技术标签:
【中文标题】PyCharm 中类型提示 dict.items() 时的奇怪行为【英文标题】:Strange behaviour when type-hinting dict.items() in PyCharm 【发布时间】:2021-06-13 04:29:04 【问题描述】:假设我有一个函数,do_something
:
from typing import Sequence, Tuple, Dict
def do_something(argument: Sequence[Tuple[int, str]]):
pass
假设我还有一本字典,D
,其键仅为int
s,其值仅为str
s:
D: Dict[int, str] = 1: 'a', 2: 'b', 3: 'c'
在 PyCharm 中,这将出色地通过类型检查器:
do_something(
((1, 'a'), (2, 'b'), (3, 'c'))
)
但是,根据 PyCharm 的说法,尽管它产生的内容相同,但类型检查器却失败了:
do_something(tuple(D.items()))
这是预期的行为 - 我在这里遗漏了什么吗? -- 或者这是 PyCharm 的类型检查器的错误?
【问题讨论】:
【参考方案1】:这是 PyCharm 中的一个错误。 有许多类似的错误,例如this, this, this.
总的来说,PyCharm 在这方面非常聪明。在您的情况下,它可以正确推断 D
的类型。它还正确地推断出D.items()
,然后在for k, v in D.items()
、k
和v
之类的代码中将被正确推断。但是由于某些奇怪的原因,tuple
/list
/sorted
或 D.items()
周围的东西是有问题的。
我总是会在您希望它可以工作时在 Youtrack 上报告问题。
【讨论】:
我仍然很想知道 Mypy 是否适合这个。【参考方案2】:PyCharm 不能保证D
的类型真的是Dict[str, int]
;它可能不会进行代码流分析以确保没有任何东西不能将非(str, int)
对添加到字典中。 (顺便说一句,您应该看看 Mypy,Python 的“规范”类型检查器是否可以。)
您也许可以添加显式类型注释以查看是否有帮助。
D: Dict[str, int] = 1: 'a', 2: 'b', 3: 'c'
【讨论】:
有道理,谢谢。是的——我尝试明确指定字典的键和值始终是一致的类型。可悲的是,什么也没做(尽管这显然不是一个大问题)。 如果添加显式类型没有帮助,则可能没有隐式或显式键入说tuple(x.items())
对于 x
即 Dict[K, V]
是 Sequence[Tuple[K, V]]
...跨度>
是的,我认为这是一个更深层次的问题。我尝试将函数本身中的类型提示调整为:def DoSomething(argument: Sequence[Tuple[Any, Any]]): pass
,但问题仍然存在。无论任何给定字典的键和值的类型是什么,在我看来 tuple(Dict.items()) 将始终是 Sequence[Tuple[Any, Any]] 类型。所以这对我来说没有逻辑意义。
嗯...试试Iterable[Tuple[K, V]]
- 我认为Sequence
s 应该是可索引的,但.items()
es 肯定不是。
还是不行!从我在另一个答案中被指出的例子来看,它看起来可能只是一个 PyCharm 错误。以上是关于PyCharm 中类型提示 dict.items() 时的奇怪行为的主要内容,如果未能解决你的问题,请参考以下文章
Python3基础 dict items 以元组的形式打印出字典的每一个项