Skip to content

Commit 5a01583

Browse files
fazeelghafoornicoddemusPierre-Sassoulas
authored
Improve approx repr for better readability (#12665)
Adjust `ApproxScalar.__repr__` to format tolerances in decimal form for smaller ranges. Closes #6985 --------- Co-authored-by: Bruno Oliveira <[email protected]> Co-authored-by: Pierre Sassoulas <[email protected]>
1 parent f0a0436 commit 5a01583

File tree

3 files changed

+37
-6
lines changed

3 files changed

+37
-6
lines changed

Diff for: changelog/6985.improvement.rst

+21
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
Improved :func:`pytest.approx` to enhance the readability of value ranges and tolerances between 0.001 and 1000.
2+
* The `repr` method now provides clearer output for values within those ranges, making it easier to interpret the results.
3+
* Previously, the output for those ranges of values and tolerances was displayed in scientific notation (e.g., `42 ± 1.0e+00`). The updated method now presents the tolerance as a decimal for better readability (e.g., `42 ± 1`).
4+
5+
Example:
6+
7+
**Previous Output:**
8+
9+
.. code-block:: console
10+
11+
>>> pytest.approx(42, abs=1)
12+
42 ± 1.0e+00
13+
14+
**Current Output:**
15+
16+
.. code-block:: console
17+
18+
>>> pytest.approx(42, abs=1)
19+
42 ± 1
20+
21+
-- by :user:`fazeelghafoor`

Diff for: src/_pytest/python_api.py

+5-1
Original file line numberDiff line numberDiff line change
@@ -406,7 +406,11 @@ def __repr__(self) -> str:
406406
# If a sensible tolerance can't be calculated, self.tolerance will
407407
# raise a ValueError. In this case, display '???'.
408408
try:
409-
vetted_tolerance = f"{self.tolerance:.1e}"
409+
if 1e-3 <= self.tolerance < 1e3:
410+
vetted_tolerance = f"{self.tolerance:n}"
411+
else:
412+
vetted_tolerance = f"{self.tolerance:.1e}"
413+
410414
if (
411415
isinstance(self.expected, Complex)
412416
and self.expected.imag

Diff for: testing/python/approx.py

+11-5
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,7 @@ def do_assert(lhs, rhs, expected_message, verbosity_level=0):
9292

9393
SOME_FLOAT = r"[+-]?([0-9]*[.])?[0-9]+\s*"
9494
SOME_INT = r"[0-9]+\s*"
95+
SOME_TOLERANCE = rf"({SOME_FLOAT}|[+-]?[0-9]+(\.[0-9]+)?[eE][+-]?[0-9]+\s*)"
9596

9697

9798
class TestApprox:
@@ -103,7 +104,7 @@ def test_error_messages_native_dtypes(self, assert_approx_raises_regex):
103104
"",
104105
" comparison failed",
105106
f" Obtained: {SOME_FLOAT}",
106-
f" Expected: {SOME_FLOAT} ± {SOME_FLOAT}",
107+
f" Expected: {SOME_FLOAT} ± {SOME_TOLERANCE}",
107108
],
108109
)
109110

@@ -119,9 +120,9 @@ def test_error_messages_native_dtypes(self, assert_approx_raises_regex):
119120
r" comparison failed. Mismatched elements: 2 / 3:",
120121
rf" Max absolute difference: {SOME_FLOAT}",
121122
rf" Max relative difference: {SOME_FLOAT}",
122-
r" Index \| Obtained\s+\| Expected ",
123-
rf" a \| {SOME_FLOAT} \| {SOME_FLOAT} ± {SOME_FLOAT}",
124-
rf" c \| {SOME_FLOAT} \| {SOME_FLOAT} ± {SOME_FLOAT}",
123+
r" Index \| Obtained\s+\| Expected\s+",
124+
rf" a \| {SOME_FLOAT} \| {SOME_FLOAT} ± {SOME_TOLERANCE}",
125+
rf" c \| {SOME_FLOAT} \| {SOME_FLOAT} ± {SOME_TOLERANCE}",
125126
],
126127
)
127128

@@ -334,6 +335,11 @@ def test_repr_string(self):
334335
"approx({'b': 2.0 ± 2.0e-06, 'a': 1.0 ± 1.0e-06})",
335336
)
336337

338+
assert repr(approx(42, abs=1)) == "42 ± 1"
339+
assert repr(approx(5, rel=0.01)) == "5 ± 0.05"
340+
assert repr(approx(24000, abs=500)) == "24000 ± 500"
341+
assert repr(approx(1500, abs=555)) == "1500 ± 555"
342+
337343
def test_repr_complex_numbers(self):
338344
assert repr(approx(inf + 1j)) == "(inf+1j)"
339345
assert repr(approx(1.0j, rel=inf)) == "1j ± inf"
@@ -347,7 +353,7 @@ def test_repr_complex_numbers(self):
347353
assert repr(approx(3 + 4 * 1j)) == "(3+4j) ± 5.0e-06 ∠ ±180°"
348354

349355
# absolute tolerance is not scaled
350-
assert repr(approx(3.3 + 4.4 * 1j, abs=0.02)) == "(3.3+4.4j) ± 2.0e-02 ∠ ±180°"
356+
assert repr(approx(3.3 + 4.4 * 1j, abs=0.02)) == "(3.3+4.4j) ± 0.02 ∠ ±180°"
351357

352358
@pytest.mark.parametrize(
353359
"value, expected_repr_string",

0 commit comments

Comments
 (0)