From: Miss Islington (bot) <31488909+miss-islington@users.noreply.github.com> Date: Tue, 10 Mar 2026 17:05:07 +0000 (+0100) Subject: [3.13] gh-144173: fix flaky test_complex.test_truediv() (GH-144355) (#145767) X-Git-Tag: v3.13.13~107 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=f349433df04090cd6c6a4934c0e5914b63afef2e;p=thirdparty%2FPython%2Fcpython.git [3.13] gh-144173: fix flaky test_complex.test_truediv() (GH-144355) (#145767) gh-144173: fix flaky test_complex.test_truediv() (GH-144355) Previously, component-wise relative error bound was tested. However, such bound can't exist already for complex multiplication as one can be used to perform subtraction of floating-point numbers, e.g. x and y for z0=1+1j and z1=x+yj. ```pycon >>> x, y = 1e-9+1j, 1+1j >>> a = x*y*y.conjugate()/2;a (1.0000000272292198e-09+1j) >>> b = x*(y*y.conjugate()/2);b (1e-09+1j) >>> b == x True >>> (a.real-b.real)/math.ulp(b.real) 131672427.0 ``` (cherry picked from commit c4333a12708a917d1cfb6418c04be45793ecc392) Co-authored-by: Sergey B Kirpichev --- diff --git a/Lib/test/test_complex.py b/Lib/test/test_complex.py index 6ff1a8ab29d0..af4eba5451ba 100644 --- a/Lib/test/test_complex.py +++ b/Lib/test/test_complex.py @@ -62,8 +62,8 @@ class ComplexTest(ComplexesAreIdenticalMixin, unittest.TestCase): else: unittest.TestCase.assertAlmostEqual(self, a, b) - def assertCloseAbs(self, x, y, eps=1e-9): - """Return true iff floats x and y "are close".""" + def assertClose(self, x, y, eps=1e-9): + """Return true iff complexes x and y "are close".""" # put the one with larger magnitude second if abs(x) > abs(y): x, y = y, x @@ -72,26 +72,15 @@ class ComplexTest(ComplexesAreIdenticalMixin, unittest.TestCase): if x == 0: return abs(y) < eps # check that relative difference < eps - self.assertTrue(abs((x-y)/y) < eps) - - def assertClose(self, x, y, eps=1e-9): - """Return true iff complexes x and y "are close".""" - self.assertCloseAbs(x.real, y.real, eps) - self.assertCloseAbs(x.imag, y.imag, eps) + self.assertTrue(abs(x-y)/abs(y) < eps) def check_div(self, x, y): """Compute complex z=x*y, and check that z/x==y and z/y==x.""" z = x * y - if x != 0: - q = z / x - self.assertClose(q, y) - q = z.__truediv__(x) - self.assertClose(q, y) - if y != 0: - q = z / y - self.assertClose(q, x) - q = z.__truediv__(y) - self.assertClose(q, x) + if x: + self.assertClose(z / x, y) + if y: + self.assertClose(z / y, x) def test_truediv(self): simple_real = [float(i) for i in range(-5, 6)] @@ -105,10 +94,20 @@ class ComplexTest(ComplexesAreIdenticalMixin, unittest.TestCase): self.check_div(complex(1e200, 1e200), 1+0j) self.check_div(complex(1e-200, 1e-200), 1+0j) + # Smith's algorithm has several sources of inaccuracy + # for components of the result. In examples below, + # it's cancellation of digits in computation of sum. + self.check_div(1e-09+1j, 1+1j) + self.check_div(8.289760544677449e-09+0.13257307440728516j, + 0.9059966714925808+0.5054864708672686j) + # Just for fun. for i in range(100): - self.check_div(complex(random(), random()), - complex(random(), random())) + x = complex(random(), random()) + y = complex(random(), random()) + self.check_div(x, y) + y = complex(1e10*y.real, y.imag) + self.check_div(x, y) self.assertAlmostEqual(complex.__truediv__(2+0j, 1+1j), 1-1j) self.assertRaises(TypeError, operator.truediv, 1j, None) @@ -343,7 +342,7 @@ class ComplexTest(ComplexesAreIdenticalMixin, unittest.TestCase): self.assertTrue(1j) def test_conjugate(self): - self.assertClose(complex(5.3, 9.8).conjugate(), 5.3-9.8j) + self.assertEqual(complex(5.3, 9.8).conjugate(), 5.3-9.8j) def test_constructor(self): def check(z, x, y):