Consider the following minimal example:
from array import array
def foo(arr: array) -> None:
print(arr)
I have a function which takes an array
argument.
My project is statically typed and uses mypy.
Mypy complains that:
Mypy: Missing type parameters for generic type "array"
.
Could you help me understand how am I supposed to type hint the argument? I can't seem to find documentation on the subject. I can't understand why would mypy decide this is a generic type.
To clarify, to my understanding, the type hint I used works, but mypy still complains as it considers it as a generic type, and wants the type of the "elements". Am I missing something, or is it a bug in mypy?
Related to this: What's the type hint for an array?
CodePudding user response:
Most of the standard library is not type annotated. mypy
is using the stubs for the standard library from the typeshed project (which along with the standard library, also contains annotations for popular third-party library as provided by various contributers). For the array
module, you can see that it is type annotated as generic:
import sys
from typing import Any, BinaryIO, Generic, Iterable, MutableSequence, Tuple, TypeVar, Union, overload
from typing_extensions import Literal
_IntTypeCode = Literal["b", "B", "h", "H", "i", "I", "l", "L", "q", "Q"]
_FloatTypeCode = Literal["f", "d"]
_UnicodeTypeCode = Literal["u"]
_TypeCode = Union[_IntTypeCode, _FloatTypeCode, _UnicodeTypeCode]
_T = TypeVar("_T", int, float, str)
typecodes: str
class array(MutableSequence[_T], Generic[_T]):
typecode: _TypeCode
itemsize: int
@overload
def __init__(self: array[int], typecode: _IntTypeCode, __initializer: bytes | Iterable[_T] = ...) -> None: ...
@overload
def __init__(self: array[float], typecode: _FloatTypeCode, __initializer: bytes | Iterable[_T] = ...) -> None: ...
@overload
def __init__(self: array[str], typecode: _UnicodeTypeCode, __initializer: bytes | Iterable[_T] = ...) -> None: ...
@overload
def __init__(self, typecode: str, __initializer: bytes | Iterable[_T] = ...) -> None: ...
def append(self, __v: _T) -> None: ...
...
The solution is to use MutableSequence
as noted as answered in the question you linked to. Note, since Python 3.9 , typing.MutableSequence
(along with things like typing.List
and typing.Dict
) have been deprecated, and the types themselves support generics, so use import collections
and collections.abc.MutableSequence