继承自列表,递归定义

Inherit List of Self, recursive definition

我想构建一个递归类型 class,其中 class 是一个包含其自身的列表。如何实现?即使 from __future__ import annotations.

似乎也不起作用
from __future__ import annotations
from typing import Union, List

class A:
    pass

class AList(List[Union[A, AList]]):
    pass

目的是利用 list 的各种内置方法,例如appendextend__iter__等,同时还可以添加自定义方法。

可以简单地 class list。它是否通过 List[Union[A, AList]] 添加任何内容来指定我将在 AList 中拥有的类型元素?

语法如下:

class AList(List[Union[A, AList]]):

我不认为这是你想要做的。它基本上说 class AListlist.

的子 class

我想这就是你想要的。这应该适用于包含 __future__ 导入的 Python 3.7+,尽管我不确定 mypy 将如何处理它(至少在 Pycharm 上看起来不错)

from __future__ import annotations

from dataclasses import dataclass


class A:
    ...


@dataclass
class AList:

    data: list[A | AList]

    @staticmethod
    def my_custom_method():
        print('Hello world!')


# creating instance of A
a = A()

# does not type check
my_list = AList(a)
my_list = AList([1, 2])

# type checks
my_list1 = AList([a])
my_list2 = AList([my_list1])

# True
assert my_list1.data[0] == a
assert my_list2.data[0] == my_list1

print(my_list1)
print(my_list2)

my_list2.my_custom_method()
# Hello world!

子class来自列表

请注意,您仍然可以通过 data 属性访问上述示例中的列表对象,该属性应该支持 appendextend 等列表操作。

如果你打算从list子class,下面的方法应该有效并且在Pycharm中也能很好地工作例如.

请注意,我在这里删除了 __future__ 导入,因为实际上不需要它;因为注释 A | AList 在这种情况下已经作为字符串向前声明。

from typing import List


class A:
    ...


class AList(List['A | AList']):

    def first_element(self):
        return self[0]


# creating instance of A
a = A()

# does not type check
my_list = AList(["testing"])
my_list = AList([1, 2])

# type checks
my_list1 = AList([a])
my_list2 = AList([my_list1])

# True
assert my_list1[0] == a
assert my_list2[0] == my_list1

print(my_list1)
print(my_list2)

elem = my_list2.first_element()
print(elem)
# [<__main__.A object at 0x103809750>]
# True
assert isinstance(elem, AList)