pytest-dev/pytest · error · TypeError

cannot compare '{actual}' to numpy.ndarray

Error message

cannot compare '{actual}' to numpy.ndarray

What it means

When comparing an actual value against approx(numpy_array), pytest's ApproxNumpy.__eq__ tries to convert the actual value to a numpy array via np.asarray(actual). If that conversion fails (e.g., the actual value is a string or an incompatible object), pytest raises TypeError because no meaningful element-wise comparison can be made.

Source

Thrown at src/_pytest/approx.py:227

        return _compare_approx(
            self.expected,
            message_data,
            number_of_elements,
            different_ids,
            max_abs_diff,
            max_rel_diff,
        )

    def __eq__(self, actual) -> bool:
        import numpy as np

        # self.expected is supposed to always be an array here.

        if not np.isscalar(actual):
            try:
                actual = np.asarray(actual)
            except Exception as e:
                raise TypeError(f"cannot compare '{actual}' to numpy.ndarray") from e

        if not np.isscalar(actual) and actual.shape != self.expected.shape:
            return False

        return super().__eq__(actual)

    def _yield_comparisons(self, actual):
        import numpy as np

        # `actual` can either be a numpy array or a scalar, it is treated in
        # `__eq__` before being passed to `ApproxBase.__eq__`, which is the
        # only method that calls this one.

        if np.isscalar(actual):
            for i in np.ndindex(self.expected.shape):
                yield actual, self.expected[i].item()
        else:
            for i in np.ndindex(self.expected.shape):

View on GitHub (pinned to 98b357f69e)

Solutions

  1. Ensure the actual value is a numpy array, list, or scalar before comparing against approx(np.array(...)).
  2. Add a type assertion before the comparison: assert isinstance(actual, np.ndarray).
  3. Fix the code under test to return the expected array type.

Example fix

# before
assert get_name() == approx(np.array([1, 2, 3]))

# after
assert get_values() == approx(np.array([1, 2, 3]))
Defensive patterns

Strategy: type-guard

Validate before calling

import numpy as np

def can_compare_as_ndarray(actual) -> bool:
    """Check if actual can be converted to a numpy array for approx comparison."""
    if np.isscalar(actual):
        return True
    try:
        np.asarray(actual)
        return True
    except Exception:
        return False

# usage:
# assert can_compare_as_ndarray(result), f'Cannot compare {type(result)} against numpy array'
# assert result == approx(expected_array)

Type guard

import numpy as np

def is_ndarray_compatible(value) -> bool:
    if np.isscalar(value):
        return True
    try:
        arr = np.asarray(value)
        return arr is not None
    except Exception:
        return False

Prevention

When it happens

Trigger: Comparing a non-array-compatible value to a numpy array approx: assert 'hello' == approx(np.array([1,2,3])). np.asarray('hello') raises, and the error is wrapped.

Common situations: A function under test returns a different type than expected (string instead of array), or a mock returns a sentinel value that is then compared against an approx array.

Related errors


AI-assisted analysis of pytest-dev/pytest@98b357f69e (2026-08-04). Data as JSON: /data/errors/0a68515ae8a245d8.json. Report an issue: GitHub.