为weakref对象列表定义python类型提示

bee*_*eep 8 python weak-references type-hinting

我还没有找到在使用弱引用时如何给出类型提示指示。

from typing import List
import weakref
class MyObject:
    def __init(self, foo)
        self.foo = foo
o1 = MyObject(1)
o2 = MyObject(2)
my_list: List[weakref] = [weakref.ref(o1), weakref.ref(o2)]
Run Code Online (Sandbox Code Playgroud)

有没有办法说my_listlistweakrefMyObject,是这样的:

my_list: List[Weakref[MyObject]] = [weakref.ref(o1), weakref.ref(o2)]
Run Code Online (Sandbox Code Playgroud)

?

Mic*_*x2a 10

我们可以通过咨询typeshed找到此信息,这是标准库和一些流行的 3rd 方模块的类型提示存储库。

具体来说,如果我们查看weakref模块的存根,我们可以看到它ref_weakref模块中重新导出。从那里,我们看到ref被定义为等价于ReferenceType被定义为泛型的类(并且也从 重新导出weakref)。

将这些部分放在一起,我们可以为您的my_list变量提供如下所示的类型提示:

from __future__ import annotations
from typing import List
from weakref import ref, ReferenceType

# ...snip...

my_list: List[ReferenceType[MyObject]] = [...]
Run Code Online (Sandbox Code Playgroud)

有点有趣的是,这样做也可以:

from __future__ import annotations
from typing import List
from weakref import ref

# ...snip...

my_list: List[ref[MyObject]] = [...]
Run Code Online (Sandbox Code Playgroud)

基本上,ref也是 to 的别名,ReferenceType因此我们可以互换使用这两种类型。

我个人会使用ReferenceType,但这主要是因为我太习惯以大写字母开头的类型。(或者,如果该类型提示开始变得过于冗长,我可能会定义一个自定义类型别名Ref = ReferenceType)。

请注意,该from __future__ import annotations行仅在 Python 3.7+ 上可用。如果您使用的是旧版本的 Python,则需要手动将类型提示设为字符串:

from typing import List
from weakref import ref

# ...snip...

my_list: "List[ReferenceType[MyObject]]" = [...]

# Or:

my_list: List["ReferenceType[MyObject]"] = [...]
Run Code Online (Sandbox Code Playgroud)

  • 确实,您的示例导致:`File "<ipython-input-61-5860728006fe>", line 1, in <module>r: ReferenceType[MyObject] = weakref.ref(o1) TypeError: 'type' object is not subscriptable` (3认同)
  • 这实际上在运行时不起作用 - 真正的“weakref.ReferenceType”不是通用的。 (2认同)