Python's typing system allows for generics in classes:
class A(Generic[T]):
def get_next(self) -> T
which is very handy. However, even in 3.11 with the Self type, I cannot find a way to change the type argument (the T
) without specifying the class name. Here's the recommended usage from PEP 673: Self Type: https://peps.python.org/pep-0673/a
class Container(Generic[T]):
def foo(
self: Container[T],
) -> Container[str]:
# maybe implementing something like:
return self.__class__([str(x) for x in self])
The problem is if I want to subclass container:
class SuperContainer(Container[T]):
def time_travel(self): ...
And then if I have an instance of SuperContainer and call foo on it, the typing will be wrong, and think that it's a Container not SuperContainer.
sc = SuperContainer([1, 2, 3])
sc2 = sc.foo()
reveal_type(sc2) # mypy: Container[str]
sc2.time_travel() # typing error: only SuperContainers can time-travel
isinstance(sc2, SuperContainer) # True
Is there an accepted way to allow a program to change the type argument in the superclass that preserves the typing of the subclass?
from Changing type argument of Python with subclassing
No comments:
Post a Comment