1

I want to check if two functions get the same result. This similarity check couldn't be done by list comparisons. The results contains both lists and NumPy arrays in nested form, so I tried to change them to ndarrays using loops and then try np.testing.assert_array_equal, but it get an unmatched shapes error:

ValueError:
error during assertion:

Traceback (most recent call last):
File "/usr/local/lib/python3.7/dist-packages/numpy/testing/_private/utils.py", line 817, in assert_array_compare
max_abs_error = max(error)
File "<array_function internals>", line 6, in amax
File "/usr/local/lib/python3.7/dist-packages/numpy/core/fromnumeric.py", line 2755, in amax keepdims=keepdims, initial=initial, where=where)
File "/usr/local/lib/python3.7/dist-packages/numpy/core/fromnumeric.py", line 86, in _wrapreduction
return ufunc.reduce(obj, axis, dtype, out, **passkwargs)
ValueError: operands could not be broadcast together with shapes (27,2,1) (26,2,1)

Arrays are not equal
x: array([array([[[0.21456296],
[0.66358573]],
...
y: array([array([[[0.21456296],
[0.66358573]],
...

I don't know why this happened and if it is related to "An exception is raised at shape mismatch or conflicting values." in its documentation; Both the functions are the same with same data inputs.
This problem can be reproduced by the following codes:

import numpy as np

cv = np.array([[1, 0], [2, 1], [3, 2], [4, 3], [5, 4]], dtype=np.int32)
vc = np.array([[0.73901752, 0.29121358], [0.43416323, 0.09588229], [0.66348142, 0.31610006],
               [0.82838408, 0.91985854], [0.80829238, 0.38857108], [0.95869708, 0.96481968],
               [0.02026681, 0.43935289], [0.95321295, 0.30348123], [0.7182516 , 0.85782094],
               [0.89697646, 0.99626489]])
change = 0.05
iters = np.arange(3, 8)
mi = np.array([[0.24122257, 0.56981744], [0.24122257, 0.14708398], [0.54651088, 0.14708398],
               [0.67472099, 0.20946646], [0.33991152, 0.36013738]])
ma = np.array([[0.66782044, 0.77456042], [0.54651088, 0.77456042], [0.69503927, 0.20946646],
               [0.69503927, 0.7711305 ], [0.67472099, 0.7711305 ]])


def ex(cv, vc, iters, change, mi, ma):
    rng = np.random.default_rng(85)
    Rand_ = []
    for i, j in enumerate(cv):
        rand_lim = []
        for m in range(iters[i]):
            rand_x = rng.uniform(mi[i, 0] - change, ma[i, 0] + change, 1)
            rand_y = rng.uniform(mi[i, 1] - change, ma[i, 1] + change, 1)
            rand_lim.append([rand_x, rand_y])
        Rand_.append(rand_lim)
    return Rand_


def new(cv, vc, iters, change, mi, ma):
    rng = np.random.default_rng(85)
    Rand_ = []
    for i, j in enumerate(cv):
        rand_lim = []
        for m in range(iters[i]):
            rand_x = rng.uniform(mi[i, 0] - change, ma[i, 0] + change, 1)
            rand_y = rng.uniform(mi[i, 1] - change, ma[i, 1] + change, 1)
            rand_lim.append([rand_x, rand_y])
        Rand_.append(rand_lim)
    return Rand_


ex_ = ex(cv, vc, iters, change, mi, ma)
new_ = new(cv, vc, iters, change, mi, ma)

ex_ = np.array([np.array(xi) for xi in ex_])
new_ = np.array([np.array(xi) for xi in new_])

# ex_ = np.array([np.array(xi, dtype=float) for xi in ex_], dtype=object)
# new_ = np.array([np.array(xi, dtype=float) for xi in new_], dtype=object)

np.testing.assert_array_equal(ex_, new_)

Why this error happened?

Ali_Sh
  • 2,667
  • 3
  • 43
  • 66
  • it's not an `AssertionError` but a `ValueError`, because `np.max` for [`error = np.abs(ex_ - new_); np.max(error)`](https://github.com/numpy/numpy/blob/4adc87dff15a247e417d50f10cc4def8e1c17a03/numpy/testing/_private/utils.py#L817) fails. I would say appropriate since your inputs are not *array_like*. – Michael Szczesny Apr 11 '22 at 08:10
  • You can iterate both lists and assert the arrays after another. – Michael Szczesny Apr 11 '22 at 08:19
  • @MichaelSzczesny, why `np.max` is failed? What do you mean by "**inputs are not array_like**", any recommendation? This can be done by two nested loops. I would be grateful if you explain more to cure without loops if it possible (may as an answer). – Ali_Sh Apr 11 '22 at 09:23
  • 1
    *ex_* shape is `(5,)`, which is a strong indicator that it's not a 2D array. `np.max` tries to reduce over axis=0 first, but fails because the inner arrays are not of equal shape. I think you can't avoid using a loop. – Michael Szczesny Apr 11 '22 at 09:44

0 Answers0