Skip to content

Conversation

@jorenham
Copy link
Member

@jorenham jorenham commented Nov 17, 2025

For most numpy.lib._function_base_impl functions, the adds support for shape-typing, improves the accuracy of returned dtypes, adds validation for callable argument signatures, and adds inline overload comments, and fixes overlapping overloads, towards #27032.

The following functions are affected:

  • np.average
  • np.asarray_chkfinite
  • np.piecewise
  • np.extract
  • np.select
  • np.copy
  • np.gradient
  • np.diff
  • np.interp
  • np.angle
  • np.unwrap
  • np.sort_complex
  • np.cov
  • np.corrcoef
  • np.blackman
  • np.bartlett
  • np.hanning
  • np.hamming
  • np.kaiser
  • np.i0
  • np.sinc
  • np.median
  • np.percentile
  • np.quantile
  • np.trapezoid
  • np.meshgrid
  • np.place
  • np.delete
  • np.insert
  • np.append
  • np.digitize

@jorenham
Copy link
Member Author

This turned out to be a lot more work than I had initially anticipated 😅

@github-actions

This comment has been minimized.

@github-actions

This comment has been minimized.

@jorenham
Copy link
Member Author

The primer error for colour is a true positive, which I addressed in colour-science/colour#1377

The primer error for optuna (src) is caused by mypy's controversial "union vs core" behavior, causing it to infer [math.nan, b, a] (where b and a are 1d arrays) as list[object]. This is not assignable to condlist: Sequence[ArrayLike], because object is not assignable to ArrayLike. So this isn't a regression or something like that.

The disappeared arviz error was indeed a false negative before, so it's good that the error is gone now.

@ngoldbaum
Copy link
Member

Ping @MarcoGorelli - any chance you can give this a once-over?

@jorenham
Copy link
Member Author

Yea that would help :).

In the meantime, let's see if mr. robot has anything useful to say about this

Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull Request Overview

This PR significantly improves typing for functions in numpy.lib._function_base_impl, adding shape-typing support, more accurate dtype specifications, validation for callable signatures, and comprehensive overloads for 30+ functions.

Key Changes:

  • Enhanced type precision with shape-aware types (e.g., _Array1D, _Array2D) and specific dtype returns
  • Expanded overloads for functions like average, median, percentile, quantile, gradient, etc. to handle different input shapes and scalar types
  • Added callable signature validation for piecewise function using ParamSpec

Reviewed Changes

Copilot reviewed 3 out of 3 changed files in this pull request and generated 4 comments.

File Description
numpy/lib/_function_base_impl.pyi Extensive typing improvements including new type aliases, overloads for shape-preservation, and more precise return types for 30+ functions
numpy/typing/tests/data/reveal/lib_function_base.pyi Updated type assertion tests to validate new typing improvements with shape-specific and dtype-specific checks
numpy/typing/tests/data/fail/lib_function_base.pyi Updated error type expectations to match new overload signatures

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

@jorenham
Copy link
Member Author

Ok I have to admit that that was a pretty solid review. I think I'll ask copilot for reviews more often now.

@github-actions
Copy link

Diff from mypy_primer, showing the effect of this PR on type check results on a corpus of open source code:

colour (https://github.com/colour-science/colour)
+ colour/models/rgb/cylindrical.py:531: error: List item 0 has incompatible type "ndarray[tuple[Any, ...], dtype[floating[_16Bit] | floating[_32Bit] | float64]]"; expected "_SupportsArray[dtype[numpy.bool[builtins.bool]]] | _NestedSequence[_SupportsArray[dtype[numpy.bool[builtins.bool]]]] | builtins.bool | _NestedSequence[builtins.bool]"  [list-item]
+ colour/models/rgb/cylindrical.py:532: error: List item 1 has incompatible type "ndarray[tuple[Any, ...], dtype[floating[_16Bit] | floating[_32Bit] | float64]]"; expected "_SupportsArray[dtype[numpy.bool[builtins.bool]]] | _NestedSequence[_SupportsArray[dtype[numpy.bool[builtins.bool]]]] | builtins.bool | _NestedSequence[builtins.bool]"  [list-item]
+ colour/models/rgb/cylindrical.py:533: error: List item 2 has incompatible type "ndarray[tuple[Any, ...], dtype[floating[_16Bit] | floating[_32Bit] | float64]]"; expected "_SupportsArray[dtype[numpy.bool[builtins.bool]]] | _NestedSequence[_SupportsArray[dtype[numpy.bool[builtins.bool]]]] | builtins.bool | _NestedSequence[builtins.bool]"  [list-item]
+ colour/models/rgb/cylindrical.py:534: error: List item 3 has incompatible type "ndarray[tuple[Any, ...], dtype[floating[_16Bit] | floating[_32Bit] | float64]]"; expected "_SupportsArray[dtype[numpy.bool[builtins.bool]]] | _NestedSequence[_SupportsArray[dtype[numpy.bool[builtins.bool]]]] | builtins.bool | _NestedSequence[builtins.bool]"  [list-item]
+ colour/models/rgb/cylindrical.py:535: error: List item 4 has incompatible type "ndarray[tuple[Any, ...], dtype[floating[_16Bit] | floating[_32Bit] | float64]]"; expected "_SupportsArray[dtype[numpy.bool[builtins.bool]]] | _NestedSequence[_SupportsArray[dtype[numpy.bool[builtins.bool]]]] | builtins.bool | _NestedSequence[builtins.bool]"  [list-item]
+ colour/models/rgb/cylindrical.py:536: error: List item 5 has incompatible type "ndarray[tuple[Any, ...], dtype[floating[_16Bit] | floating[_32Bit] | float64]]"; expected "_SupportsArray[dtype[numpy.bool[builtins.bool]]] | _NestedSequence[_SupportsArray[dtype[numpy.bool[builtins.bool]]]] | builtins.bool | _NestedSequence[builtins.bool]"  [list-item]

optuna (https://github.com/optuna/optuna)
+ optuna/samplers/_tpe/_truncnorm.py:262: error: No overload variant of "select" matches argument types "list[Any]", "list[object]", "ndarray[tuple[Any, ...], dtype[Any]]"  [call-overload]
+ optuna/samplers/_tpe/_truncnorm.py:262: note: Possible overload variants:
+ optuna/samplers/_tpe/_truncnorm.py:262: note:     def [_ArrayT: ndarray[tuple[Any, ...], dtype[Any]]] select(condlist: _SizedIterable[_SupportsArray[dtype[numpy.bool[builtins.bool]]] | _NestedSequence[_SupportsArray[dtype[numpy.bool[builtins.bool]]]] | builtins.bool | _NestedSequence[builtins.bool]], choicelist: Sequence[_ArrayT], default: complex | str | bytes | generic[Any] = ...) -> _ArrayT
+ optuna/samplers/_tpe/_truncnorm.py:262: note:     def [_ScalarT: generic[Any]] select(condlist: _SizedIterable[_SupportsArray[dtype[numpy.bool[builtins.bool]]] | _NestedSequence[_SupportsArray[dtype[numpy.bool[builtins.bool]]]] | builtins.bool | _NestedSequence[builtins.bool]], choicelist: Sequence[_SupportsArray[dtype[_ScalarT]] | _NestedSequence[_SupportsArray[dtype[_ScalarT]]]] | ndarray[tuple[Any, ...], dtype[_ScalarT]], default: complex | str | bytes | generic[Any] = ...) -> ndarray[tuple[Any, ...], dtype[_ScalarT]]
+ optuna/samplers/_tpe/_truncnorm.py:262: note:     def select(condlist: _SizedIterable[_SupportsArray[dtype[numpy.bool[builtins.bool]]] | _NestedSequence[_SupportsArray[dtype[numpy.bool[builtins.bool]]]] | builtins.bool | _NestedSequence[builtins.bool]], choicelist: Sequence[Buffer | _SupportsArray[dtype[Any]] | _NestedSequence[_SupportsArray[dtype[Any]]] | complex | bytes | str | _NestedSequence[complex | bytes | str]], default: complex | str | bytes | generic[Any] = ...) -> ndarray[tuple[Any, ...], dtype[Any]]

arviz (https://github.com/arviz-devs/arviz)
- arviz/stats/ecdf_utils.py:324: error: Incompatible return value type (got "floating[Any]", expected "float")  [return-value]

@charris charris merged commit debb9a3 into numpy:main Nov 24, 2025
21 checks passed
@charris
Copy link
Member

charris commented Nov 24, 2025

Thanks Joren.

@jorenham jorenham deleted the typing/lib._function_base_impl branch November 24, 2025 16:36
cakedev0 pushed a commit to cakedev0/numpy that referenced this pull request Dec 5, 2025
* TYP: ``lib._function_base_impl``: many typing improvements

* TYP: use the any trick when calling ``gradiant`` with arrays of unknown shape

* TYP: fix regression in ``append`` caught by mypy_primer

* TYP: Apply Copilot's review suggestions (yes, they actually made sense)
IndifferentArea pushed a commit to IndifferentArea/numpy that referenced this pull request Dec 7, 2025
* TYP: ``lib._function_base_impl``: many typing improvements

* TYP: use the any trick when calling ``gradiant`` with arrays of unknown shape

* TYP: fix regression in ``append`` caught by mypy_primer

* TYP: Apply Copilot's review suggestions (yes, they actually made sense)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants