Fixed Bug Regarding Attribute Error in pytest.approx For Types Implicitly Convertible to Numpy Arrays (#12232)
* added test case in testing/python/approx.py based on test case provided by reporter in issue #12114 * test cases pass for pytest testing/python/approx.py * expanded the type annotation to include objects which may cast to a array and renamed other_side to other_side_as_array and asserted that it is not none
This commit is contained in:
parent
a830a3e98d
commit
5cffef7f07
1
AUTHORS
1
AUTHORS
|
@ -321,6 +321,7 @@ Pierre Sassoulas
|
||||||
Pieter Mulder
|
Pieter Mulder
|
||||||
Piotr Banaszkiewicz
|
Piotr Banaszkiewicz
|
||||||
Piotr Helm
|
Piotr Helm
|
||||||
|
Poulami Sau
|
||||||
Prakhar Gurunani
|
Prakhar Gurunani
|
||||||
Prashant Anand
|
Prashant Anand
|
||||||
Prashant Sharma
|
Prashant Sharma
|
||||||
|
|
|
@ -0,0 +1 @@
|
||||||
|
Fixed attribute error in pytest.approx for types implicitly convertible to numpy arrays by converting other_side to a numpy array so that np_array_shape != other_side.shape can be properly checked.
|
|
@ -142,7 +142,7 @@ class ApproxNumpy(ApproxBase):
|
||||||
)
|
)
|
||||||
return f"approx({list_scalars!r})"
|
return f"approx({list_scalars!r})"
|
||||||
|
|
||||||
def _repr_compare(self, other_side: "ndarray") -> List[str]:
|
def _repr_compare(self, other_side: Union["ndarray", List[Any]]) -> List[str]:
|
||||||
import itertools
|
import itertools
|
||||||
import math
|
import math
|
||||||
|
|
||||||
|
@ -163,10 +163,14 @@ class ApproxNumpy(ApproxBase):
|
||||||
self._approx_scalar, self.expected.tolist()
|
self._approx_scalar, self.expected.tolist()
|
||||||
)
|
)
|
||||||
|
|
||||||
if np_array_shape != other_side.shape:
|
# convert other_side to numpy array to ensure shape attribute is available
|
||||||
|
other_side_as_array = _as_numpy_array(other_side)
|
||||||
|
assert other_side_as_array is not None
|
||||||
|
|
||||||
|
if np_array_shape != other_side_as_array.shape:
|
||||||
return [
|
return [
|
||||||
"Impossible to compare arrays with different shapes.",
|
"Impossible to compare arrays with different shapes.",
|
||||||
f"Shapes: {np_array_shape} and {other_side.shape}",
|
f"Shapes: {np_array_shape} and {other_side_as_array.shape}",
|
||||||
]
|
]
|
||||||
|
|
||||||
number_of_elements = self.expected.size
|
number_of_elements = self.expected.size
|
||||||
|
@ -175,7 +179,7 @@ class ApproxNumpy(ApproxBase):
|
||||||
different_ids = []
|
different_ids = []
|
||||||
for index in itertools.product(*(range(i) for i in np_array_shape)):
|
for index in itertools.product(*(range(i) for i in np_array_shape)):
|
||||||
approx_value = get_value_from_nested_list(approx_side_as_seq, index)
|
approx_value = get_value_from_nested_list(approx_side_as_seq, index)
|
||||||
other_value = get_value_from_nested_list(other_side, index)
|
other_value = get_value_from_nested_list(other_side_as_array, index)
|
||||||
if approx_value != other_value:
|
if approx_value != other_value:
|
||||||
abs_diff = abs(approx_value.expected - other_value)
|
abs_diff = abs(approx_value.expected - other_value)
|
||||||
max_abs_diff = max(max_abs_diff, abs_diff)
|
max_abs_diff = max(max_abs_diff, abs_diff)
|
||||||
|
@ -188,7 +192,7 @@ class ApproxNumpy(ApproxBase):
|
||||||
message_data = [
|
message_data = [
|
||||||
(
|
(
|
||||||
str(index),
|
str(index),
|
||||||
str(get_value_from_nested_list(other_side, index)),
|
str(get_value_from_nested_list(other_side_as_array, index)),
|
||||||
str(get_value_from_nested_list(approx_side_as_seq, index)),
|
str(get_value_from_nested_list(approx_side_as_seq, index)),
|
||||||
)
|
)
|
||||||
for index in different_ids
|
for index in different_ids
|
||||||
|
|
|
@ -763,6 +763,23 @@ class TestApprox:
|
||||||
assert a12 != approx(a21)
|
assert a12 != approx(a21)
|
||||||
assert a21 != approx(a12)
|
assert a21 != approx(a12)
|
||||||
|
|
||||||
|
def test_numpy_array_implicit_conversion(self):
|
||||||
|
np = pytest.importorskip("numpy")
|
||||||
|
|
||||||
|
class ImplicitArray:
|
||||||
|
"""Type which is implicitly convertible to a numpy array."""
|
||||||
|
|
||||||
|
def __init__(self, vals):
|
||||||
|
self.vals = vals
|
||||||
|
|
||||||
|
def __array__(self, dtype=None, copy=None):
|
||||||
|
return np.array(self.vals)
|
||||||
|
|
||||||
|
vec1 = ImplicitArray([1.0, 2.0, 3.0])
|
||||||
|
vec2 = ImplicitArray([1.0, 2.0, 4.0])
|
||||||
|
# see issue #12114 for test case
|
||||||
|
assert vec1 != approx(vec2)
|
||||||
|
|
||||||
def test_numpy_array_protocol(self):
|
def test_numpy_array_protocol(self):
|
||||||
"""
|
"""
|
||||||
array-like objects such as tensorflow's DeviceArray are handled like ndarray.
|
array-like objects such as tensorflow's DeviceArray are handled like ndarray.
|
||||||
|
|
Loading…
Reference in New Issue