使用TypeV的函数的pytype引发失败

2024-06-25 06:02:27 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在使用pytype(2019.10.17,到现在为止的最新版本)作为我的代码类型检查器来开发一个工具,它能够通过使用索引文件随机读取msgpack文件,该文件记录每个消息(存储在msgpack中的值)的位置(msgpack文件中的偏移量)。根据消息类型的多样性,我使用typing.TypeVar来实现泛型类型。pytype使用TypeVar时遇到问题

Name: pytype
Version: 2019.10.17
Summary: Python type inferencer
Home-page: https://google.github.io/pytype
Author: None
Author-email: None
License: UNKNOWN
Location: /home/gaoyunpeng/miniconda3/envs/restore/lib/python3.6/site-packages
Requires: ninja, typed-ast, six, importlab, pyyaml, attrs
Required-by:
Python 3.6.4 :: Anaconda, Inc.
from typing import TypeVar
T = TypeVar('T')

def f(x: T): 
  print(x)

使用以下命令运行上述代码:pytype main2.py

Computing dependencies
Analyzing 1 sources with 0 local dependencies
ninja: Entering directory `/home/gaoyunpeng/workspace/.pytype'
[1/1] check main2
FAILED: /home/gaoyunpeng/workspace/.pytype/pyi/main2.pyi 
pytype-single --imports_info /home/gaoyunpeng/workspace/.pytype/imports/main2.imports --module-name main2 -V 3.6 -o /home/gaoyunpeng/workspace/.pytype/pyi/main2.pyi --analyze-annotated --nofail --quick /home/gaoyunp
eng/workspace/main2.py
File "/home/gaoyunpeng/workspace/main2.py", line 4, in <module>: Invalid type annotation 'T'  [invalid-annotation]
  Appears only once in the signature

For more details, see https://google.github.io/pytype/errors.html#invalid-annotation.
ninja: build stopped: subcommand failed.

正如https://google.github.io/pytype/errors.html#invalid-annotation所述,这种情况是无效的注释

我想知道为什么代码不能通过pytype检查


Tags: 文件代码httpsgithub类型homegoogleannotation
1条回答
网友
1楼 · 发布于 2024-06-25 06:02:27

打印出的错误消息解释了这是类型错误的原因。就像节目里说的。引用错误消息的相关部分:

File "/home/gaoyunpeng/workspace/main2.py", line 4, in <module>: Invalid type annotation 'T'  [invalid-annotation]
  Appears only once in the signature

在给定的签名中只使用一次TypeVar是错误的,因为这样做毫无意义。在您的例子中,您最好只使用类型签名def f(x: object) -> None。你想说f可以接受任何东西,Python中的所有东西都是object的子类型

只有在坚持两个或多个类型完全相同时,才应该使用泛型类型。例如,如果要定义“identity”函数,使用泛型类型是正确的:

def identity(x: T) -> T:
    return x

这将允许类型检查器推断identity("foo")identity(4)分别属于str和int类型,返回类型始终与参数类型相同

注意,对于泛型类中的方法,这个“每次签名都应该使用TypeVar两次或更多次”规则也是正确的。当您这样做时:

class Foo(Generic[T]):
    def test(self, x: T) -> None: pass

…签名test实际上是def test(self: Foo[T], x: T) -> None。所以我们总是隐式地使用TypeVar两次

相关问题 更多 >