[Python] Python overload doesn't match `Any` case

Discussão em 'Python' iniciado por Stack, Março 14, 2025.

  1. Stack

    Stack Membro Participativo

    I've written this code:

    from typing import overload, TYPE_CHECKING, Protocol, Any

    import pyarrow as pa # type: ignore[import-not-found]

    class PyArrowArray(Protocol):
    @property
    def buffers(self) -> Any: ...

    @overload
    def func(a: PyArrowArray) -> int: ...
    @overload
    def func(a: str) -> str: ...
    @overload
    def func(a: Any) -> str | int: ...


    def func(a) -> str | int:
    if isinstance(a, pa.Array):
    return 0
    return '0'

    reveal_type(func(pa.array([1,2,3])))


    PyArrow is a Python library which does not have type hints. However, there is a package pyarrow-stubs which provides types for it.

    I have a function can accept either a pyarrow.Array or a str:

    • if it receives a pyarrow.Array, it returns an int
    • if it receives a str, it returns a str

    I would like to annotate it such that:

    • if a user has pyarrow-stubs installed, then func(pa.array([1,2,3])) is revealed to be int
    • if a user doesn't have pyarrow-stubs installed, then func(pa.array([1,2,3])) should be revealed to be int | str, because pa is not known statically

    I was hoping that the code above would accomplish that, but it doesn't. If pyarrow-stubs is not installed, I get

    Revealed type is "Any"


    I was expecting that the

    @overload
    def func(a: Any) -> str | int: ...


    overload would be matched and that I'd get Revealed type is int | str

    Continue reading...

Compartilhe esta Página