From 2c087c12b8d7c2ee93a0ac4714e05216facdcfea Mon Sep 17 00:00:00 2001 From: Tim Hoffmann <2836374+timhoffm@users.noreply.github.com> Date: Thu, 13 Feb 2025 23:49:17 +0100 Subject: [PATCH] FIX: Fix unit example so that we can unpin numpy>2.1 Closes #28780. The underlying problem is that operations on numpy scalars try to eagerly convert the other operand to an array. As a result `scalar = np .float64 (2); scalar * radians` would result in a numpy scalar. But we don't want that. Instead we enforce `radians.__rmul__(scalar)` by giving the unit a higher `__array_priority__`. See also https://github .com/numpy/numpy/issues/17650. I haven't found any specific change notes on this in numpy 2.1. Interestingly, the full story is even more complex. Also for numpy<2.1 `radians.__rmul__(scalar)` is not called, but there seems another mechanism through __array__ and __array_warp__ catching back in so that the result is again a TaggedValue. But I have not fully investigated why it worked previously. In fact, we want the solution here with going through __rmul__, and that works for all numpy versions. ` --- .circleci/config.yml | 2 +- environment.yml | 2 +- galleries/examples/units/basic_units.py | 5 +++++ 3 files changed, 7 insertions(+), 2 deletions(-) diff --git a/.circleci/config.yml b/.circleci/config.yml index e7348b868d4b..40ba933cf0d9 100644 --- a/.circleci/config.yml +++ b/.circleci/config.yml @@ -98,7 +98,7 @@ commands: parameters: numpy_version: type: string - default: "~=2.0.0" + default: "" steps: - run: name: Install Python dependencies diff --git a/environment.yml b/environment.yml index 7b9ff51ae325..7593700f247a 100644 --- a/environment.yml +++ b/environment.yml @@ -18,7 +18,7 @@ dependencies: - kiwisolver>=1.3.1 - pybind11>=2.13.2 - meson-python>=0.13.1 - - numpy<2.1 + - numpy - pillow>=9 - pkg-config - pygobject diff --git a/galleries/examples/units/basic_units.py b/galleries/examples/units/basic_units.py index 3f64d145b65e..486918a8eafc 100644 --- a/galleries/examples/units/basic_units.py +++ b/galleries/examples/units/basic_units.py @@ -193,6 +193,11 @@ def get_unit(self): class BasicUnit: + # numpy scalars convert eager and np.float64(2) * BasicUnit('cm') + # would thus return a numpy scalar. To avoid this, we increase the + # priority of the BasicUnit. + __array_priority__ = np.float64(0).__array_priority__ + 1 + def __init__(self, name, fullname=None): self.name = name if fullname is None: