From b536c16052b45b079c00a0b2a4088b98e420d98b Mon Sep 17 00:00:00 2001 From: Sergey B Kirpichev Date: Mon, 13 Nov 2023 12:50:37 +0300 Subject: [PATCH 1/9] Port test/test_gmpy2_mpfr_misc.txt to pytest framework --- test/test_functions.py | 119 +++++++++++++++++-- test/test_gmpy2_mpfr_misc.txt | 214 ---------------------------------- test/test_mpc.py | 2 + test/test_mpfr.py | 57 ++++++++- 4 files changed, 166 insertions(+), 226 deletions(-) delete mode 100644 test/test_gmpy2_mpfr_misc.txt diff --git a/test/test_functions.py b/test/test_functions.py index fb9aa3ba..6d1e8945 100644 --- a/test/test_functions.py +++ b/test/test_functions.py @@ -1,15 +1,17 @@ import pytest import gmpy2 -from gmpy2 import (can_round, fac, fma, fmma, fmms, fms, from_binary, get_exp, - ieee, is_bpsw_prp, is_euler_prp, is_extra_strong_lucas_prp, - is_fermat_prp, is_fibonacci_prp, is_finite, is_infinite, - is_lucas_prp, is_nan, is_selfridge_prp, is_strong_bpsw_prp, - is_strong_lucas_prp, is_strong_prp, is_strong_selfridge_prp, - is_zero, maxnum, minnum, mpc, mpfr, mpfr_from_old_binary, - mpq, mpq_from_old_binary, mpz, mpz_from_old_binary, norm, +from gmpy2 import (can_round, check_range, copy_sign, f2q, fac, fma, fmma, + fmms, fms, from_binary, get_emax_max, get_emin_min, get_exp, + ieee, inf, is_bpsw_prp, is_euler_prp, + is_extra_strong_lucas_prp, is_fermat_prp, is_fibonacci_prp, + is_finite, is_infinite, is_lucas_prp, is_nan, + is_selfridge_prp, is_strong_bpsw_prp, is_strong_lucas_prp, + is_strong_prp, is_strong_selfridge_prp, is_zero, maxnum, + minnum, mpc, mpfr, mpfr_from_old_binary, mpq, + mpq_from_old_binary, mpz, mpz_from_old_binary, nan, norm, phase, polar, powmod, powmod_sec, proj, rect, root, - root_of_unity, rootn, set_exp, zero) + root_of_unity, rootn, set_exp, set_sign, zero) def test_root(): @@ -401,3 +403,104 @@ def test_is_finite(): assert is_finite(mpc("0+nanj")) is False assert is_finite(mpc("0+infj")) is False assert is_finite(mpc("inf+3j")) is False + + +def test_f2q(): + a = mpfr('123.456') + + pytest.raises(TypeError, lambda: f2q('a')) + pytest.raises(TypeError, lambda: f2q(1,2,3,4)) + + assert f2q(a,0.1) == mpz(123) + assert f2q(a,0.01) == mpz(123) + assert f2q(a,0.001) == mpq(247,2) + assert f2q(a,0.0001) == mpq(1358,11) + assert f2q(a,0.00001) == mpq(7037,57) + assert f2q(a,0.000001) == mpq(15432,125) + assert f2q(a,0.0000001) == mpq(15432,125) + assert f2q(a) == mpq(15432,125) + assert f2q(2.50000000000008) == mpq(15637498706148,6254999482459) + assert f2q(2.5000000000000) == mpq(5,2) + assert f2q(2.50000000000008, 0.001) == mpq(5,2) + assert f2q(2.50000000000008, -50) == mpq(15637498706148,6254999482459) + assert f2q(mpfr('0.500000011'), 1e-4) == mpq(1,2) + assert f2q(mpfr('0.500000011'), 1e-5) == mpq(1,2) + assert f2q(mpfr('0.500000011'), 1e-6) == mpq(1,2) + assert f2q(mpfr('0.500000011'), 1e-7) == mpq(1,2) + assert f2q(mpfr('0.500000011'), 1e-8) == mpq(22727273,45454545) + assert f2q(mpfr('0.500000011'), 1e-9) == mpq(22727273,45454545) + assert f2q(mpfr('0.500000011'), 1e-10) == mpq(22727273,45454545) + assert f2q(mpfr('0.500000011'), 1e-11) == mpq(22727273,45454545) + assert f2q(mpfr('0.500000011'), 1e-12) == mpq(22727273,45454545) + assert f2q(mpfr('0.500000011'), 1e-13) == mpq(22727273,45454545) + assert f2q(mpfr('0.500000011'), 1e-14) == mpq(22727273,45454545) + assert f2q(mpfr('0.500000011'), 1e-15) == mpq(22727273,45454545) + assert f2q(mpfr('0.500000011'), 1e-16) == mpq(204545458,409090907) + assert f2q(mpfr('0.500000011'), 1e-17) == mpq(204545458,409090907) + + +def test_get_emin_min(): + assert get_emin_min() in (-4611686018427387903, -1073741823) + + +def test_get_emax_max(): + assert get_emax_max() in (4611686018427387903, 1073741823) + + +def test_get_exp(): + assert get_exp(mpfr(5.232)) == 3 + + pytest.raises(TypeError, lambda: get_exp(0)) + + assert get_exp(mpfr('inf')) == 0 + assert get_exp(mpfr(0)) == 0 + + +def test_set_exp(): + r = mpfr(4.55) + + assert set_exp(r, 4) == mpfr('9.0999999999999996') + + pytest.raises(TypeError, lambda: set_exp(r, mpz(4))) + + +def test_set_sign(): + r = mpfr(4.55) + + assert set_sign(r, False) == mpfr('4.5499999999999998') + assert set_sign(r, True) == mpfr('-4.5499999999999998') + + pytest.raises(TypeError, lambda: set_sign(mpz(5), True)) + pytest.raises(TypeError, lambda: set_sign(r, 'oiio')) + + +def test_copy_sign(): + assert copy_sign(mpfr(4), mpfr(-2)) == mpfr('-4.0') + + pytest.raises(TypeError, lambda: copy_sign(mpfr(4), True)) + + +def test_nan(): + x = nan() + + assert is_nan(x) + + +def test_inf(): + assert inf() == mpfr('inf') + assert inf(-5) == mpfr('-inf') + assert inf(mpz(-30)) == mpfr('-inf') + + pytest.raises(TypeError, lambda: inf(mpfr(30))) + + +def test_check_range(): + r = mpfr(4.55) + + assert check_range(r) == mpfr('4.5499999999999998') + + ctx = gmpy2.get_context() + + assert ctx.check_range(r) == mpfr('4.5499999999999998') + + pytest.raises(TypeError, lambda: ctx.check_range(mpz(5))) diff --git a/test/test_gmpy2_mpfr_misc.txt b/test/test_gmpy2_mpfr_misc.txt deleted file mode 100644 index a56591da..00000000 --- a/test/test_gmpy2_mpfr_misc.txt +++ /dev/null @@ -1,214 +0,0 @@ -Test gmpy2_mpfr_misc -==================== - ->>> import gmpy2 ->>> from gmpy2 import mpz, mpq, mpfr, mpc ->>> ctx = gmpy2.get_context() ->>> a = mpfr('123.456') ->>> r = mpfr(4.55) ->>> gmpy2.f2q('a') -Traceback (most recent call last): - .... -TypeError: f2q() argument types not supported ->>> gmpy2.f2q(1,2,3,4) -Traceback (most recent call last): - .... -TypeError: f2q() requires 1 or 2 arguments ->>> gmpy2.f2q(a,0.1) -mpz(123) ->>> gmpy2.f2q(a,0.01) -mpz(123) ->>> gmpy2.f2q(a,0.001) -mpq(247,2) ->>> gmpy2.f2q(a,0.0001) -mpq(1358,11) ->>> gmpy2.f2q(a,0.00001) -mpq(7037,57) ->>> gmpy2.f2q(a,0.000001) -mpq(15432,125) ->>> gmpy2.f2q(a,0.0000001) -mpq(15432,125) ->>> gmpy2.f2q(a) -mpq(15432,125) ->>> gmpy2.f2q(2.50000000000008) -mpq(15637498706148,6254999482459) ->>> gmpy2.f2q(2.5000000000000) -mpq(5,2) ->>> gmpy2.f2q(2.50000000000008, 0.001) -mpq(5,2) ->>> gmpy2.f2q(2.50000000000008, -50) -mpq(15637498706148,6254999482459) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-4) -mpq(1,2) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-5) -mpq(1,2) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-6) -mpq(1,2) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-7) -mpq(1,2) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-8) -mpq(22727273,45454545) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-9) -mpq(22727273,45454545) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-10) -mpq(22727273,45454545) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-11) -mpq(22727273,45454545) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-12) -mpq(22727273,45454545) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-13) -mpq(22727273,45454545) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-14) -mpq(22727273,45454545) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-15) -mpq(22727273,45454545) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-16) -mpq(204545458,409090907) ->>> gmpy2.f2q(gmpy2.mpfr('0.500000011'), 1e-17) -mpq(204545458,409090907) - ->>> gmpy2.free_cache() ->>> gmpy2.get_emin_min() in (-4611686018427387903, -1073741823) -True ->>> gmpy2.get_emax_max() in (4611686018427387903, 1073741823) -True ->>> mprec = gmpy2.get_max_precision() ->>> gmpy2.get_exp(mpfr(5.232)) -3 ->>> gmpy2.get_exp(0) -Traceback (most recent call last): - File "", line 1, in -TypeError: get_exp() requires 'mpfr' argument ->>> gmpy2.get_exp(mpfr('inf')) -0 ->>> gmpy2.get_exp(mpfr(0)) -0 - ->>> gmpy2.set_exp(r, 4) -mpfr('9.0999999999999996') ->>> gmpy2.set_exp(r, mpz(4)) -Traceback (most recent call last): - File "", line 1, in -TypeError: set_exp() requires 'mpfr', 'integer' arguments - ->>> gmpy2.set_sign(r, False) -mpfr('4.5499999999999998') ->>> gmpy2.set_sign(r, True) -mpfr('-4.5499999999999998') ->>> gmpy2.set_sign(mpz(5), True) -Traceback (most recent call last): - File "", line 1, in -TypeError: set_sign() requires 'mpfr', 'boolean' arguments ->>> gmpy2.set_sign(r, 'oiio') -Traceback (most recent call last): - File "", line 1, in -TypeError: set_sign() requires 'mpfr', 'boolean' arguments ->>> 1 -1 - ->>> gmpy2.copy_sign(mpfr(4), mpfr(-2)) -mpfr('-4.0') ->>> gmpy2.copy_sign(mpfr(4), True) -Traceback (most recent call last): - File "", line 1, in -TypeError: copy_sign() requires 'mpfr', 'mpfr' arguments ->>> 1 -1 - ->>> nan = gmpy2.nan(); nan -mpfr('nan') ->>> inf = gmpy2.inf(); inf -mpfr('inf') ->>> gmpy2.inf(-5) -mpfr('-inf') ->>> gmpy2.inf(mpfr(30)) -Traceback (most recent call last): - File "", line 1, in -TypeError: could not convert object to integer ->>> gmpy2.inf(mpz(-30)) -mpfr('-inf') - ->>> nan.as_integer_ratio() -Traceback (most recent call last): - File "", line 1, in -ValueError: Cannot pass NaN to mpfr.as_integer_ratio. ->>> inf.as_integer_ratio() -Traceback (most recent call last): - File "", line 1, in -OverflowError: Cannot pass Infinity to mpfr.as_integer_ratio. ->>> mpfr(1.5).as_integer_ratio() -(mpz(3), mpz(2)) - ->>> r.as_mantissa_exp() -(mpz(5122844576133939), mpz(-50)) ->>> inf.as_mantissa_exp() -Traceback (most recent call last): - File "", line 1, in -OverflowError: Cannot pass Infinity to mpfr.as_mantissa_exp. ->>> nan.as_mantissa_exp() -Traceback (most recent call last): - File "", line 1, in -ValueError: Cannot pass NaN to mpfr.as_mantissa_exp. ->>> mpfr(0).as_mantissa_exp() -(mpz(0), mpz(1)) - ->>> r.as_simple_fraction() -mpq(91,20) ->>> r.as_simple_fraction(precision=100) -Traceback (most recent call last): - File "", line 1, in -ValueError: Requested precision out-of-bounds. ->>> r.as_simple_fraction(nosense=10) -Traceback (most recent call last): - File "", line 1, in -TypeError: 'nosense' is an invalid keyword argument for this function ->>> 1 -1 - ->>> r.imag -mpfr('0.0') ->>> r.real -mpfr('4.5499999999999998') ->>> not mpfr(0) -True ->>> not mpfr(1) -False ->>> r.conjugate() -mpfr('4.5499999999999998') ->>> gmpy2.check_range(r) -mpfr('4.5499999999999998') ->>> ctx = gmpy2.get_context() ->>> ctx.check_range(r) -mpfr('4.5499999999999998') ->>> ctx.check_range(mpz(5)) -Traceback (most recent call last): - File "", line 1, in -TypeError: check_range() argument types not supported ->>> 1 -1 - ->>> r.__round__(1) -mpfr('4.5') ->>> mpfr('5.1').__round__() -mpz(5) ->>> nan.__round__() -Traceback (most recent call last): - File "", line 1, in -ValueError: 'mpz' does not support NaN ->>> inf.__round__() -Traceback (most recent call last): - File "", line 1, in -OverflowError: 'mpz' does not support Infinity ->>> r.__round__(4,5) -Traceback (most recent call last): - File "", line 1, in -TypeError: __round__() requires 0 or 1 argument ->>> 1 -1 - -Test underscore ---------------- ->>> mpfr('1._3_5e4_5') -mpfr('1.3499999999999999e+45') ->>> mpc('1_2+4_5j') -mpc('12.0+45.0j') diff --git a/test/test_mpc.py b/test/test_mpc.py index 535f3bf0..e80119d5 100644 --- a/test/test_mpc.py +++ b/test/test_mpc.py @@ -107,6 +107,8 @@ def test_mpc_creation(): assert mpc(x.real, x.imag, precision=(70,37)) == x + assert mpc('1_2+4_5j') == mpc('12.0+45.0j') + def test_mpc_random(): assert (mpc_random(random_state(42)) diff --git a/test/test_mpfr.py b/test/test_mpfr.py index c6cddf6a..b7020182 100644 --- a/test/test_mpfr.py +++ b/test/test_mpfr.py @@ -9,9 +9,9 @@ from supportclasses import a, b, c, d, q, r, z import gmpy2 -from gmpy2 import (cmp, cmp_abs, from_binary, gamma_inc, is_nan, mpc, mpfr, - mpfr_grandom, mpfr_nrandom, mpq, mpz, nan, random_state, - to_binary, xmpz, zero) +from gmpy2 import (cmp, cmp_abs, from_binary, gamma_inc, inf, is_nan, mpc, + mpfr, mpfr_grandom, mpfr_nrandom, mpq, mpz, nan, + random_state, to_binary, xmpz, zero) def test_mpfr_gamma_inc(): @@ -54,7 +54,7 @@ def test_mpfr_cmp(): def test_mpfr_comparisons(): - from supportclasses import a, r, q + from supportclasses import a, q, r assert mpfr(1.5) == q assert r == mpfr(1.5) @@ -121,6 +121,7 @@ def test_mpfr_create(): assert mpfr(1) == mpfr('1.0') assert mpfr(-1) == mpfr('-1.0') assert mpfr("123e17") == mpfr('1.23e+19') + assert mpfr('1._3_5e4_5') == mpfr('1.3499999999999999e+45') pytest.raises(ValueError, lambda: mpfr("foo")) @@ -359,6 +360,11 @@ def test_mpfr_abs(): assert abs(mpfr('-inf')) == mpfr('inf') +def test_mpfr_not(): + assert not mpfr(0) + assert not mpfr(1) is False + + def test_mpfr_sub(): assert mpfr(10) - 1 == mpfr('9.0') assert 10 - mpfr(1) == mpfr('9.0') @@ -525,6 +531,9 @@ def fmt(v): def test_mpfr_as_integer_ratio(): assert mpfr('1.1e+2').as_integer_ratio() == (mpz(110), mpz(1)) + pytest.raises(ValueError, lambda: mpfr('nan').as_integer_ratio()) + pytest.raises(OverflowError, lambda: mpfr('inf').as_integer_ratio()) + def test_mpfr_round(): pytest.raises(TypeError, lambda: round(mpfr('1.0'), "spam")) @@ -533,3 +542,43 @@ def test_mpfr_round(): assert r.is_zero() and r.is_signed() assert round(mpfr('12.34'), -1) == mpfr('10.0') + + r = mpfr(4.55) + + assert round(r, 1) == mpfr('4.5') + assert round(mpfr('5.1')) == mpz(5) + + pytest.raises(ValueError, lambda: round(nan())) + pytest.raises(OverflowError, lambda: round(inf())) + + +def test_mpfr_as_mantissa_exp(): + r = mpfr(4.55) + + assert r.as_mantissa_exp() == (mpz(5122844576133939), mpz(-50)) + assert mpfr(0).as_mantissa_exp() == (mpz(0), mpz(1)) + + pytest.raises(OverflowError, lambda: inf().as_mantissa_exp()) + pytest.raises(ValueError, lambda: nan().as_mantissa_exp()) + + +def test_mpfr_as_simple_fraction(): + r = mpfr(4.55) + + assert r.as_simple_fraction() == mpq(91,20) + + pytest.raises(ValueError, lambda: r.as_simple_fraction(precision=100)) + pytest.raises(TypeError, lambda: r.as_simple_fraction(nosense=10)) + + +def test_mpfr_real_imag(): + r = mpfr(4.55) + + assert r.imag == mpfr('0.0') + assert r.real == mpfr('4.5499999999999998') + + +def test_mpfr_conjugate(): + r = mpfr(4.55) + + assert r.conjugate() == r From 16c7b6be1e8d8a714f7e73ea01170597d68f4dcc Mon Sep 17 00:00:00 2001 From: Sergey B Kirpichev Date: Thu, 16 Nov 2023 05:21:44 +0300 Subject: [PATCH 2/9] Port test/test_mpq.txt to pytest framework --- test/runtests.py | 4 +- test/test_functions.py | 12 +- test/test_mpq.py | 258 +++++++++++++++++++++- test/test_mpq.txt | 472 ----------------------------------------- 4 files changed, 268 insertions(+), 478 deletions(-) delete mode 100644 test/test_mpq.txt diff --git a/test/runtests.py b/test/runtests.py index acfc9e69..fdc0fc77 100644 --- a/test/runtests.py +++ b/test/runtests.py @@ -26,8 +26,6 @@ mpz_doctests = ["test_mpz.txt"] -mpq_doctests = ["test_mpq.txt"] - mpfr_doctests = ["test_mpfr.txt", "test_mpfr_trig.txt", "test_context.txt"] @@ -38,7 +36,7 @@ failed = 0 attempted = 0 -all_doctests = gmpy2_tests + mpz_doctests + mpq_doctests +all_doctests = gmpy2_tests + mpz_doctests all_doctests += mpfr_doctests diff --git a/test/test_functions.py b/test/test_functions.py index 6d1e8945..987e2000 100644 --- a/test/test_functions.py +++ b/test/test_functions.py @@ -11,7 +11,7 @@ minnum, mpc, mpfr, mpfr_from_old_binary, mpq, mpq_from_old_binary, mpz, mpz_from_old_binary, nan, norm, phase, polar, powmod, powmod_sec, proj, rect, root, - root_of_unity, rootn, set_exp, set_sign, zero) + root_of_unity, rootn, set_exp, set_sign, sign, zero) def test_root(): @@ -504,3 +504,13 @@ def test_check_range(): assert ctx.check_range(r) == mpfr('4.5499999999999998') pytest.raises(TypeError, lambda: ctx.check_range(mpz(5))) + + +def test_sign(): + a = mpq(3,11) + + assert sign(a) == 1 + assert sign(-a) == -1 + assert sign(mpq(0,5)) == 0 + + pytest.raises(TypeError, lambda: sign('str')) diff --git a/test/test_mpq.py b/test/test_mpq.py index 9f5d52ae..23e520b6 100644 --- a/test/test_mpq.py +++ b/test/test_mpq.py @@ -11,8 +11,8 @@ from supportclasses import a, b, c, d, q, z import gmpy2 -from gmpy2 import (cmp, cmp_abs, from_binary, mpc, mpfr, mpq, mpz, to_binary, - xmpz) +from gmpy2 import (cmp, cmp_abs, from_binary, is_nan, mpc, mpfr, mpq, mpz, + to_binary, xmpz) def test_mpz_constructor(): @@ -180,6 +180,24 @@ def test_mpq_abs(): assert a == mpq(-12,7) +def test_mpq_add(): + a = mpq(3,11) + + assert a + float('Inf') == mpfr('inf') + assert float('Inf') + a == mpfr('inf') + assert a + float('-Inf') == mpfr('-inf') + assert float('-Inf') + a == mpfr('-inf') + assert is_nan(a + float('nan')) + assert is_nan(float('nan') + a) + + assert a + mpfr('Inf') == mpfr('inf') + assert mpfr('Inf') + a == mpfr('inf') + assert a + mpfr('-Inf') == mpfr('-inf') + assert mpfr('-Inf') + a == mpfr('-inf') + assert is_nan(a + mpfr('nan')) + assert is_nan(mpfr('nan') + a) + + def test_mpq_sub(): assert mpq(1,2) - Fraction(3,2) == mpq(-1,1) assert Fraction(1,2) - mpq(3,2) == mpq(-1,1) @@ -206,6 +224,37 @@ def test_mpq_sub(): pytest.raises(TypeError, lambda: mpq(1,2) - 'a') pytest.raises(TypeError, lambda: 'a' - mpq(1,2)) + a = mpq(3,11) + b = mpq(1,2) + c = Fraction(5,7) + + assert a-b == mpq(-5,22) + assert b-a == mpq(5,22) + assert a-1 == mpq(-8,11) + assert 1-a == mpq(8,11) + assert a-c == mpq(-34,77) + assert c-a == mpq(34,77) + assert a-a == mpq(0,1) + assert a-mpz(123456) == mpq(-1358013,11) + assert mpz(-123456)-a == mpq(-1358019,11) + + pytest.raises(TypeError, lambda: a-'b') + pytest.raises(TypeError, lambda: 'b'-a) + + assert a - float('Inf') == mpfr('-inf') + assert float('Inf') - a == mpfr('inf') + assert a - float('-Inf') == mpfr('inf') + assert float('-Inf') - a == mpfr('-inf') + assert is_nan(a - float('nan')) + assert is_nan(float('nan') - a) + + assert a - mpfr('Inf') == mpfr('-inf') + assert mpfr('Inf') - a == mpfr('inf') + assert a - mpfr('-Inf') == mpfr('inf') + assert mpfr('-Inf') - a == mpfr('-inf') + assert is_nan(a - mpfr('nan')) + assert is_nan(mpfr('nan') - a) + def test_mpq_mul(): assert mpq(1,2) * Fraction(3,2) == mpq(3,4) @@ -230,8 +279,92 @@ def test_mpq_mul(): pytest.raises(TypeError, lambda: mpq(1,2) * 'a') pytest.raises(TypeError, lambda: 'a' * mpq(1,2)) + a = mpq(3,11) + b = mpq(1,2) + + assert a*b == mpq(3,22) + assert b*a == mpq(3,22) + assert a*0 == mpq(0,1) + assert 0*a == mpq(0,1) + assert a*-1 == mpq(-3,11) + assert -1*a == mpq(-3,11) + assert a*mpz(17) == mpq(51,11) + assert mpz(17)*a == mpq(51,11) + assert a*a == mpq(9,121) + + pytest.raises(TypeError, lambda: a*'b') + pytest.raises(TypeError, lambda: 'b'*a) + + assert a * float('Inf') == mpfr('inf') + assert float('Inf') * a == mpfr('inf') + assert a * float('-Inf') == mpfr('-inf') + assert float('-Inf') * a == mpfr('-inf') + assert -a * float('Inf') == mpfr('-inf') + assert float('Inf') * -a == mpfr('-inf') + assert -a * float('-Inf') == mpfr('inf') + assert float('-Inf') * -a == mpfr('inf') + assert is_nan(a * float('nan')) + assert is_nan(float('nan') * a) + assert is_nan(mpz(0) * float('Inf')) + assert is_nan(mpz(0) * float('-Inf')) + assert is_nan(float('Inf') * mpz(0)) + assert is_nan(float('-Inf') * mpz(0)) + + assert a * mpfr('Inf') == mpfr('inf') + assert mpfr('Inf') * a == mpfr('inf') + assert a * mpfr('-Inf') == mpfr('-inf') + assert mpfr('-Inf') * a == mpfr('-inf') + assert -a * mpfr('Inf') == mpfr('-inf') + assert mpfr('Inf') * -a == mpfr('-inf') + assert -a * mpfr('-Inf') == mpfr('inf') + assert mpfr('-Inf') * -a == mpfr('inf') + assert is_nan(a * mpfr('nan')) + assert is_nan(mpfr('nan') * a) + assert is_nan(mpz(0) * mpfr('Inf')) + assert is_nan(mpz(0) * mpfr('-Inf')) + assert is_nan(mpfr('Inf') * mpz(0)) + assert is_nan(mpfr('-Inf') * mpz(0)) + + +def test_mpq_mod(): + a = mpq(3,11) + b = mpq(1,2) + ctx = gmpy2.get_context() + + assert a%b == mpq(3,11) + assert b%a == mpq(5,22) + assert a%z == mpq(3,11) + assert mpq(3,1) % q == mpq(0,1) + + pytest.raises(ZeroDivisionError, lambda: a % mpq(0,5)) + + assert ctx.mod(a, mpfr(1.5)) == mpfr('0.27272727272727271') + + pytest.raises(TypeError, lambda: ctx.mod(a, mpc(0.5, 2))) + pytest.raises(ZeroDivisionError, lambda: ctx.mod(a, mpq(0, 2))) + + assert a % mpfr(1.5) == mpfr('0.27272727272727271') + + pytest.raises(TypeError, lambda: a % mpc(0.5, 2)) + pytest.raises(TypeError, lambda: a % 'str') + pytest.raises(TypeError, lambda: ctx.mod(a, 'str')) + def test_mpq_divmod(): + a = mpq(3,11) + b = mpq(1,2) + c = Fraction(5,7) + ctx = gmpy2.get_context() + + assert divmod(a,b) == (mpz(0), mpq(3,11)) + assert divmod(b,a) == (mpz(1), mpq(5,22)) + + pytest.raises(ZeroDivisionError, lambda: divmod(a,0)) + + assert divmod(17,a) == (mpz(62), mpq(1,11)) + assert divmod(mpz(17),a) == (mpz(62), mpq(1,11)) + assert divmod(a,c) == (mpz(0), mpq(3,11)) + pytest.raises(TypeError, lambda: divmod(mpq(1,2),'a')) ctx = gmpy2.ieee(64) @@ -241,6 +374,44 @@ def test_mpq_divmod(): pytest.raises(TypeError, lambda: divmod(mpq(1,2), mpc(1,2))) + assert divmod(a, float('Inf')) == (mpfr('0.0'), mpfr('0.27272727272727271')) + assert divmod(a, float('-Inf')) == (mpfr('-1.0'), mpfr('-inf')) + assert divmod(-a, float('Inf')) == (mpfr('-1.0'), mpfr('inf')) + assert divmod(-a, float('-Inf')) == (mpfr('0.0'), mpfr('-0.27272727272727271')) + assert all(map(is_nan, divmod(a, float('nan')))) + assert all(map(is_nan, divmod(-a, float('nan')))) + assert divmod(mpz(0), float('Inf')) == (mpfr('0.0'), mpfr('0.0')) + assert divmod(mpz(0), float('-Inf')) == (mpfr('-0.0'), mpfr('-0.0')) + assert all(map(is_nan, divmod(mpz(0), float('nan')))) + assert all(map(is_nan, divmod(float('Inf'), a))) + assert all(map(is_nan, divmod(float('-Inf'), a))) + assert all(map(is_nan, divmod(float('Inf'), -a))) + assert all(map(is_nan, divmod(float('-Inf'), -a))) + assert all(map(is_nan, divmod(float('nan'), a))) + assert all(map(is_nan, divmod(float('nan'), -a))) + assert all(map(is_nan, divmod(float('Inf'), mpz(0)))) + assert all(map(is_nan, divmod(float('-Inf'), mpz(0)))) + assert all(map(is_nan, divmod(float('nan'), mpz(0)))) + + assert divmod(a, mpfr('Inf')) == (mpfr('0.0'), mpfr('0.27272727272727271')) + assert divmod(a, mpfr('-Inf')) == (mpfr('-1.0'), mpfr('-inf')) + assert divmod(-a, mpfr('Inf')) == (mpfr('-1.0'), mpfr('inf')) + assert divmod(-a, mpfr('-Inf')) == (mpfr('0.0'), mpfr('-0.27272727272727271')) + assert all(map(is_nan, divmod(a, mpfr('nan')))) + assert all(map(is_nan, divmod(-a, mpfr('nan')))) + assert divmod(mpz(0), mpfr('Inf')) == (mpfr('0.0'), mpfr('0.0')) + assert divmod(mpz(0), mpfr('-Inf')) == (mpfr('-0.0'), mpfr('-0.0')) + assert divmod(mpz(0), mpfr('nan')) + assert divmod(mpfr('Inf'), a) + assert divmod(mpfr('-Inf'), a) + assert divmod(mpfr('Inf'), -a) + assert divmod(mpfr('-Inf'), -a) + assert divmod(mpfr('nan'), a) + assert divmod(mpfr('nan'), -a) + assert divmod(mpfr('Inf'), mpz(0)) + assert divmod(mpfr('-Inf'), mpz(0)) + assert divmod(mpfr('nan'), mpz(0)) + def test_mpq_floordiv(): ctx = gmpy2.get_context() @@ -269,6 +440,65 @@ def test_mpq_floordiv(): pytest.raises(TypeError, lambda: q // c2) pytest.raises(TypeError, lambda: q // 'not') + a = mpq(3,11) + b = mpq(1,2) + + assert a//b == mpz(0) + assert b//a == mpz(1) + + pytest.raises(ZeroDivisionError, lambda: a//0) + + assert 0//a == mpz(0) + assert mpq(355, 113) // 2 == mpz(1) + assert mpq(355, 113) // mpz(2) == mpz(1) + assert mpq(355, 113) // z == mpz(1) + + +def test_mpq_truediv(): + a = mpq(3,11) + b = mpq(1,2) + ctx = gmpy2.get_context() + + assert a/b == mpq(6,11) + assert gmpy2.div(a, b) == mpq(6,11) + assert ctx.div(a, b) == mpq(6,11) + assert b/a == mpq(11,6) + + pytest.raises(ZeroDivisionError, lambda: a/0) + + assert 0/a == mpq(0,1) + assert a / z == mpq(3,22) + assert mpq(3,11) / q == mpq(2,11) + assert a / mpc(5, 4) == mpc('0.03325942350332594-0.02660753880266075j') + + pytest.raises(ZeroDivisionError, lambda: a / mpq(0,1)) + pytest.raises(TypeError, lambda: a / 'str') + + assert a / float('Inf') == mpfr('0.0') + assert -a / float('Inf') == mpfr('-0.0') + assert float('Inf') / a == mpfr('inf') + assert float('Inf') / -a == mpfr('-inf') + assert a / float('-Inf') == mpfr('-0.0') + assert -a / float('-Inf') == mpfr('0.0') + assert float('-Inf') / a == mpfr('-inf') + assert float('-Inf') / -a == mpfr('inf') + assert is_nan(a / float('nan')) + assert is_nan(float('nan') / a) + assert is_nan(float('nan') / mpz(0)) + + assert a / mpfr('Inf') == mpfr('0.0') + assert -a / mpfr('Inf') == mpfr('-0.0') + assert mpfr('Inf') / a == mpfr('inf') + assert mpfr('Inf') / -a == mpfr('-inf') + assert a / mpfr('-Inf') == mpfr('-0.0') + assert -a / mpfr('-Inf') == mpfr('0.0') + assert mpfr('-Inf') / a == mpfr('-inf') + assert mpfr('-Inf') / -a == mpfr('inf') + assert is_nan(a / mpfr('nan')) + assert is_nan(mpfr('nan') / a) + assert is_nan(mpfr('nan') / mpz(0)) + assert is_nan(mpfr('nan') / mpz(0)) + def test_mpq_pow(): q = mpq(2,3) @@ -286,6 +516,7 @@ def test_mpq_pow(): def test_mpq_attributes(): q = mpq('4/5') + a = mpq(3,11) pyq = Fraction(4, 5) assert q.numerator == mpz(4) @@ -293,6 +524,11 @@ def test_mpq_attributes(): assert gmpy2.numer(q) == mpz(4) assert gmpy2.denom(q) == mpz(5) + assert a.numerator == mpz(3) + assert a.denominator == mpz(11) + assert a.real == mpq(3,11) + assert a.imag == mpz(0) + pytest.raises(TypeError, lambda: gmpy2.numer(6.2)) pytest.raises(TypeError, lambda: gmpy2.denom(5.6)) pytest.raises(TypeError, lambda: gmpy2.denom(mpfr(5))) @@ -301,6 +537,12 @@ def test_mpq_attributes(): assert gmpy2.denom(pyq) == mpz(5) +def test_mpq_conjugate(): + a = mpq(3, 11) + + assert a.conjugate() == a + + def test_mpq_floor(): assert math.floor(mpq('7/2')) == mpz(3) @@ -345,6 +587,18 @@ def test_mpq_qdiv(): assert gmpy2.qdiv(10, q) == mpq(25,2) assert gmpy2.qdiv(1) == mpz(1) + assert gmpy2.qdiv(8,1) == mpz(8) + assert gmpy2.qdiv(8,2) == mpz(4) + assert gmpy2.qdiv(8,3) == mpq(8,3) + assert gmpy2.qdiv(8,4) == mpz(2) + assert gmpy2.qdiv(mpq(3,4), mpq(1,3)) == mpq(9,4) + assert gmpy2.qdiv(mpq(3,4), mpq(1,4)) == mpz(3) + + args = mpq(2), 1/gmpy2.mpq(2) + + assert gmpy2.qdiv(*args) == mpz(4) + assert args == (mpq(2), 1/mpq(2)) + def test_issue_334(): x = mpq(3,2) diff --git a/test/test_mpq.txt b/test/test_mpq.txt deleted file mode 100644 index 3b3a6979..00000000 --- a/test/test_mpq.txt +++ /dev/null @@ -1,472 +0,0 @@ -MPQ Functionality -================= - -Testing of mpq functionality is split into multiple files. - ->>> import gmpy2 as G ->>> ctx = G.get_context() ->>> from fractions import Fraction as F ->>> from gmpy2 import mpz, mpq, mpfr, mpc ->>> from supportclasses import * ->>> a = mpq(3,11) ->>> b = mpq(1,2) ->>> c = F(5,7) - -Test elementary operations -========================== - -Test subtraction ----------------- - ->>> a-b -mpq(-5,22) ->>> b-a -mpq(5,22) ->>> a-1 -mpq(-8,11) ->>> 1-a -mpq(8,11) ->>> a-c -mpq(-34,77) ->>> c-a -mpq(34,77) ->>> a-a -mpq(0,1) ->>> a-mpz(123456) -mpq(-1358013,11) ->>> mpz(-123456)-a -mpq(-1358019,11) ->>> a-'b' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for -: 'mpq' and 'str' ->>> 'b'-a -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for -: 'str' and 'mpq' ->>> 1 -1 - -Test multiplication -------------------- - ->>> a*b -mpq(3,22) ->>> b*a -mpq(3,22) ->>> a*0 -mpq(0,1) ->>> 0*a -mpq(0,1) ->>> a*-1 -mpq(-3,11) ->>> -1*a -mpq(-3,11) ->>> a*mpz(17) -mpq(51,11) ->>> mpz(17)*a -mpq(51,11) ->>> a*a -mpq(9,121) ->>> a*'b' -Traceback (most recent call last): - File "", line 1, in -TypeError: can't multiply sequence by non-int of type 'mpq' ->>> 'b'*a -Traceback (most recent call last): - File "", line 1, in -TypeError: can't multiply sequence by non-int of type 'mpq' ->>> 1 -1 - -Test division -------------- - ->>> a//b -mpz(0) ->>> b//a -mpz(1) ->>> a/b -mpq(6,11) ->>> gmpy2.div(a, b) -mpq(6,11) ->>> ctx.div(a, b) -mpq(6,11) ->>> b/a -mpq(11,6) ->>> a/0 -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> a//0 -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> 0//a -mpz(0) ->>> 0/a -mpq(0,1) ->>> mpq(355, 113) // 2 -mpz(1) ->>> mpq(355, 113) // mpz(2) -mpz(1) ->>> a / z -mpq(3,22) ->>> mpq(355, 113) // z -mpz(1) ->>> mpq(3,11) / q -mpq(2,11) ->>> mpq(3,11) // q -mpz(0) ->>> a / mpc(5, 4) -mpc('0.03325942350332594-0.02660753880266075j') ->>> a / mpq(0,1) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> a / 'str' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for /: 'mpq' and 'str' ->>> 1 -1 - -Test modulo ------------ - ->>> a%b -mpq(3,11) ->>> b%a -mpq(5,22) ->>> a%z -mpq(3,11) ->>> mpq(3,1) % q -mpq(0,1) ->>> divmod(a,b) -(mpz(0), mpq(3,11)) ->>> divmod(b,a) -(mpz(1), mpq(5,22)) ->>> divmod(a,0) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: 'mpq' division or modulo by zero ->>> a % mpq(0,5) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> ctx.mod(a, mpfr(1.5)) -mpfr('0.27272727272727271') ->>> ctx.mod(a, mpc(0.5, 2)) -Traceback (most recent call last): - File "", line 1, in -TypeError: can't take mod of complex number ->>> ctx.mod(a, mpq(0, 2)) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> divmod(17,a) -(mpz(62), mpq(1,11)) ->>> divmod(mpz(17),a) -(mpz(62), mpq(1,11)) ->>> divmod(a,c) -(mpz(0), mpq(3,11)) ->>> a % mpfr(1.5) -mpfr('0.27272727272727271') ->>> a % mpc(0.5, 2) -Traceback (most recent call last): - File "", line 1, in -TypeError: can't take mod of complex number ->>> a % 'str' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for %: 'mpq' and 'str' ->>> ctx.mod(a, 'str') -Traceback (most recent call last): - File "", line 1, in -TypeError: mod() argument type not supported ->>> 1 -1 - -Test operations involving NaN/Inf ---------------------------------- - ->>> a + float('Inf') -mpfr('inf') ->>> float('Inf') + a -mpfr('inf') ->>> a + float('-Inf') -mpfr('-inf') ->>> float('-Inf') + a -mpfr('-inf') ->>> a + float('nan') -mpfr('nan') ->>> float('nan') + a -mpfr('nan') ->>> a - float('Inf') -mpfr('-inf') ->>> float('Inf') - a -mpfr('inf') ->>> a - float('-Inf') -mpfr('inf') ->>> float('-Inf') - a -mpfr('-inf') ->>> a - float('nan') -mpfr('nan') ->>> float('nan') - a -mpfr('nan') ->>> a * float('Inf') -mpfr('inf') ->>> float('Inf') * a -mpfr('inf') ->>> a * float('-Inf') -mpfr('-inf') ->>> float('-Inf') * a -mpfr('-inf') ->>> -a * float('Inf') -mpfr('-inf') ->>> float('Inf') * -a -mpfr('-inf') ->>> -a * float('-Inf') -mpfr('inf') ->>> float('-Inf') * -a -mpfr('inf') ->>> a * float('nan') -mpfr('nan') ->>> float('nan') * a -mpfr('nan') ->>> G.mpz(0) * float('Inf') -mpfr('nan') ->>> G.mpz(0) * float('-Inf') -mpfr('nan') ->>> float('Inf') * G.mpz(0) -mpfr('nan') ->>> float('-Inf') * G.mpz(0) -mpfr('nan') ->>> a / float('Inf') -mpfr('0.0') ->>> -a / float('Inf') -mpfr('-0.0') ->>> float('Inf') / a -mpfr('inf') ->>> float('Inf') / -a -mpfr('-inf') ->>> a / float('-Inf') -mpfr('-0.0') ->>> -a / float('-Inf') -mpfr('0.0') ->>> float('-Inf') / a -mpfr('-inf') ->>> float('-Inf') / -a -mpfr('inf') ->>> a / float('nan') -mpfr('nan') ->>> float('nan') / a -mpfr('nan') ->>> float('nan') / G.mpz(0) -mpfr('nan') ->>> float('nan') / G.mpz(0) -mpfr('nan') - ->>> a + mpfr('Inf') -mpfr('inf') ->>> mpfr('Inf') + a -mpfr('inf') ->>> a + mpfr('-Inf') -mpfr('-inf') ->>> mpfr('-Inf') + a -mpfr('-inf') ->>> a + mpfr('nan') -mpfr('nan') ->>> mpfr('nan') + a -mpfr('nan') ->>> a - mpfr('Inf') -mpfr('-inf') ->>> mpfr('Inf') - a -mpfr('inf') ->>> a - mpfr('-Inf') -mpfr('inf') ->>> mpfr('-Inf') - a -mpfr('-inf') ->>> a - mpfr('nan') -mpfr('nan') ->>> mpfr('nan') - a -mpfr('nan') ->>> a * mpfr('Inf') -mpfr('inf') ->>> mpfr('Inf') * a -mpfr('inf') ->>> a * mpfr('-Inf') -mpfr('-inf') ->>> mpfr('-Inf') * a -mpfr('-inf') ->>> -a * mpfr('Inf') -mpfr('-inf') ->>> mpfr('Inf') * -a -mpfr('-inf') ->>> -a * mpfr('-Inf') -mpfr('inf') ->>> mpfr('-Inf') * -a -mpfr('inf') ->>> a * mpfr('nan') -mpfr('nan') ->>> mpfr('nan') * a -mpfr('nan') ->>> G.mpz(0) * mpfr('Inf') -mpfr('nan') ->>> G.mpz(0) * mpfr('-Inf') -mpfr('nan') ->>> mpfr('Inf') * G.mpz(0) -mpfr('nan') ->>> mpfr('-Inf') * G.mpz(0) -mpfr('nan') ->>> a / mpfr('Inf') -mpfr('0.0') ->>> -a / mpfr('Inf') -mpfr('-0.0') ->>> mpfr('Inf') / a -mpfr('inf') ->>> mpfr('Inf') / -a -mpfr('-inf') ->>> a / mpfr('-Inf') -mpfr('-0.0') ->>> -a / mpfr('-Inf') -mpfr('0.0') ->>> mpfr('-Inf') / a -mpfr('-inf') ->>> mpfr('-Inf') / -a -mpfr('inf') ->>> a / mpfr('nan') -mpfr('nan') ->>> mpfr('nan') / a -mpfr('nan') ->>> mpfr('nan') / G.mpz(0) -mpfr('nan') ->>> mpfr('nan') / G.mpz(0) -mpfr('nan') - ->>> divmod(a, float('Inf')) -(mpfr('0.0'), mpfr('0.27272727272727271')) ->>> divmod(a, float('-Inf')) -(mpfr('-1.0'), mpfr('-inf')) ->>> divmod(-a, float('Inf')) -(mpfr('-1.0'), mpfr('inf')) ->>> divmod(-a, float('-Inf')) -(mpfr('0.0'), mpfr('-0.27272727272727271')) ->>> divmod(a, float('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(-a, float('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(G.mpz(0), float('Inf')) -(mpfr('0.0'), mpfr('0.0')) ->>> divmod(G.mpz(0), float('-Inf')) -(mpfr('-0.0'), mpfr('-0.0')) ->>> divmod(G.mpz(0), float('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('-Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('-Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('nan'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('nan'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('Inf'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('-Inf'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('nan'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) - ->>> divmod(a, mpfr('Inf')) -(mpfr('0.0'), mpfr('0.27272727272727271')) ->>> divmod(a, mpfr('-Inf')) -(mpfr('-1.0'), mpfr('-inf')) ->>> divmod(-a, mpfr('Inf')) -(mpfr('-1.0'), mpfr('inf')) ->>> divmod(-a, mpfr('-Inf')) -(mpfr('0.0'), mpfr('-0.27272727272727271')) ->>> divmod(a, mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(-a, mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(G.mpz(0), mpfr('Inf')) -(mpfr('0.0'), mpfr('0.0')) ->>> divmod(G.mpz(0), mpfr('-Inf')) -(mpfr('-0.0'), mpfr('-0.0')) ->>> divmod(G.mpz(0), mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) ->>> 1 -1 - -Test qdiv ---------- - ->>> gmpy2.qdiv(8,1) -mpz(8) ->>> gmpy2.qdiv(8,2) -mpz(4) ->>> gmpy2.qdiv(8,3) -mpq(8,3) ->>> gmpy2.qdiv(8,4) -mpz(2) ->>> gmpy2.qdiv(gmpy2.mpq(3,4), gmpy2.mpq(1,3)) -mpq(9,4) ->>> gmpy2.qdiv(gmpy2.mpq(3,4), gmpy2.mpq(1,4)) -mpz(3) ->>> args = gmpy2.mpq(2), 1/gmpy2.mpq(2) ->>> gmpy2.qdiv(*args) -mpz(4) ->>> args == (gmpy2.mpq(2), 1/gmpy2.mpq(2)) -True - -Test Number Protocol --------------------- - ->>> a.numerator -mpz(3) ->>> a.denominator -mpz(11) ->>> a.real -mpq(3,11) ->>> a.imag -mpz(0) ->>> a.conjugate() -mpq(3,11) - -Test sign function ------------------- - ->>> gmpy2.sign(a) -1 ->>> gmpy2.sign(-a) --1 ->>> gmpy2.sign(mpq(0,5)) -0 ->>> gmpy2.sign('str') -Traceback (most recent call last): - File "", line 1, in -TypeError: sign() argument type not supported ->>> 1 -1 From 1a2e5beae6c8c6b1922e798d65da971ecff6b96a Mon Sep 17 00:00:00 2001 From: Sergey B Kirpichev Date: Thu, 16 Nov 2023 05:53:14 +0300 Subject: [PATCH 3/9] Port test/test_context.txt to pytest framework --- test/runtests.py | 3 +- test/test_context.py | 142 +++++++++++++++++- test/test_context.txt | 335 ------------------------------------------ 3 files changed, 142 insertions(+), 338 deletions(-) delete mode 100644 test/test_context.txt diff --git a/test/runtests.py b/test/runtests.py index fdc0fc77..9da87b5b 100644 --- a/test/runtests.py +++ b/test/runtests.py @@ -26,8 +26,7 @@ mpz_doctests = ["test_mpz.txt"] -mpfr_doctests = ["test_mpfr.txt", - "test_mpfr_trig.txt", "test_context.txt"] +mpfr_doctests = ["test_mpfr.txt", "test_mpfr_trig.txt"] gmpy2_tests = [os.path.basename(i) for i in glob.glob(os.path.join(test_dir, diff --git a/test/test_context.py b/test/test_context.py index 86fcd103..d8dd1356 100644 --- a/test/test_context.py +++ b/test/test_context.py @@ -1,5 +1,8 @@ +import pytest + import gmpy2 -from gmpy2 import mpc, mpfr, mpz +from gmpy2 import (context, get_context, ieee, local_context, mpc, mpfr, mpz, + set_context) def test_context_abs(): @@ -14,3 +17,140 @@ def test_context_abs(): assert ctx.abs(mpfr(-2)) == mpfr('2.0') assert ctx.abs(2+3j) == mpfr('3.6055512754639891') assert ctx.abs(mpc(2+3j)) == mpfr('3.6055512754639891') + + +def test_context_ieee(): + ctx = ieee(32) + + assert (ctx.precision == 24 and ctx.emax == 128 and + ctx.emin == -148 and ctx.subnormalize) + + ctx = ieee(64) + + assert (ctx.precision == 53 and ctx.emax == 1024 and + ctx.emin == -1073 and ctx.subnormalize) + + ctx = ieee(128) + + assert (ctx.precision == 113 and ctx.emax == 16384 and + ctx.emin == -16493 and ctx.subnormalize) + + ctx = ieee(256) + + assert (ctx.precision == 237 and ctx.emax == 262144 and + ctx.emin == -262377 and ctx.subnormalize) + + pytest.raises(ValueError, lambda: ieee(-1)) + pytest.raises(TypeError, lambda: ieee("a")) + + set_context(ieee(32)) + + assert gmpy2.const_pi().digits(2) == ('110010010000111111011011', 2, 24) + + set_context(ieee(64)) + + assert gmpy2.const_pi().digits(2) == ('11001001000011111101101010100010001000010110100011000', 2, 53) + + set_context(ieee(128)) + + assert gmpy2.const_pi().digits(2) == ('11001001000011111101101010100010001000010110100011000010001101001100010011000110011000101000101110000000110111000', 2, 113) + + +def test_context(): + ctx = context() + + assert (ctx.precision == 53 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + ctx = context(precision=100) + + assert (ctx.precision == 100 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + ctx = context(real_prec=100) + + assert (ctx.precision == 53 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize and + ctx.real_prec == 100) + + ctx = context(real_prec=100,imag_prec=200) + + assert (ctx.precision == 53 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize and + ctx.real_prec == 100 and ctx.imag_prec == 200) + + +def test_get_context(): + set_context(context()) + + ctx = get_context() + + assert (ctx.precision == 53 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + ctx = get_context() + ctx.precision = 100 + + assert (ctx.precision == 100 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + ctx = get_context() + + assert (ctx.precision == 100 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + b = ctx.copy() + b.precision = 200 + + assert (b.precision == 200 and b.emax == 1073741823 and + b.emin == -1073741823 and not b.subnormalize) + assert (ctx.precision == 100 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + ctx = get_context() + + assert (ctx.precision == 100 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + +def test_local_context(): + set_context(context()) + + with local_context() as ctx: + assert ctx.precision == 53 + ctx.precision += 20 + assert ctx.precision == 73 + + ctx = get_context() + + assert (ctx.precision == 53 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + with local_context(ieee(64)) as ctx: + assert (ctx.precision == 53 and ctx.emax == 1024 and + ctx.emin == -1073 and ctx.subnormalize) + + ctx = get_context() + + assert (ctx.precision == 53 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + with get_context() as ctx: + assert ctx.precision == 53 + ctx.precision += 100 + assert ctx.precision == 153 + + ctx = get_context() + + assert (ctx.precision == 53 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) + + with local_context(precision=200) as ctx: + assert ctx.precision == 200 + ctx.precision += 100 + assert ctx.precision == 300 + + ctx = get_context() + + assert (ctx.precision == 53 and ctx.emax == 1073741823 and + ctx.emin == -1073741823 and not ctx.subnormalize) diff --git a/test/test_context.txt b/test/test_context.txt deleted file mode 100644 index 76d24e12..00000000 --- a/test/test_context.txt +++ /dev/null @@ -1,335 +0,0 @@ -Test context handling ---------------------- - ->>> import gmpy2 ->>> from gmpy2 import mpfr,mpc,get_context,set_context,ieee,context,local_context - -Test ieee() ------------ - ->>> ieee(32) -context(precision=24, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=128, emin=-148, - subnormalize=True, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> ieee(64) -context(precision=53, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1024, emin=-1073, - subnormalize=True, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> ieee(128) -context(precision=113, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=16384, emin=-16493, - subnormalize=True, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> gmpy2.ieee(256) -context(precision=237, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=262144, emin=-262377, - subnormalize=True, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> gmpy2.ieee(-1) -Traceback (most recent call last): - File "", line 1, in -ValueError: bitwidth must be 16, 32, 64, 128; or must be greater than 128 and divisible by 32. ->>> gmpy2.ieee("a") -Traceback (most recent call last): - File "", line 1, in -TypeError: ieee() requires 'int' argument ->>> set_context(ieee(32)) ->>> gmpy2.const_pi().digits(2) -('110010010000111111011011', 2, 24) ->>> set_context(ieee(64)) ->>> gmpy2.const_pi().digits(2) -('11001001000011111101101010100010001000010110100011000', 2, 53) ->>> set_context(ieee(128)) ->>> gmpy2.const_pi().digits(2) -('11001001000011111101101010100010001000010110100011000010001101001100010011000110011000101000101110000000110111000', 2, 113) - -Test context() --------------- - ->>> context() -context(precision=53, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> context(precision=100) -context(precision=100, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> context(real_prec=100) -context(precision=53, real_prec=100, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> context(real_prec=100,imag_prec=200) -context(precision=53, real_prec=100, imag_prec=200, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) - -Test get_context() ------------------- - ->>> set_context(context()) ->>> get_context() -context(precision=53, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> a=get_context() ->>> a.precision=100 ->>> a -context(precision=100, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> get_context() -context(precision=100, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> b=a.copy() ->>> b.precision=200 ->>> b -context(precision=200, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> a -context(precision=100, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> get_context() -context(precision=100, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) - -Test local_context() --------------------- - ->>> set_context(context()) ->>> with local_context() as ctx: -... print(ctx.precision) -... ctx.precision+=20 -... print(ctx.precision) -... -53 -73 ->>> get_context() -context(precision=53, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> with local_context(ieee(64)) as ctx: -... print(ctx) -... -context(precision=53, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1024, emin=-1073, - subnormalize=True, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> get_context() -context(precision=53, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> with get_context() as ctx: -... print(ctx.precision) -... ctx.precision+=100 -... print(ctx.precision) -... -53 -153 ->>> get_context() -context(precision=53, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) ->>> with local_context(precision=200) as ctx: -... print(ctx.precision) -... ctx.precision+=100 -... print(ctx.precision) -... -200 -300 ->>> get_context() -context(precision=53, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=False, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) - - From 967070b36ae27ac7573a3fa8ffd14f4f65221223 Mon Sep 17 00:00:00 2001 From: Sergey B Kirpichev Date: Thu, 16 Nov 2023 06:43:08 +0300 Subject: [PATCH 4/9] Port test/test_mpfr.txt to pytest framework --- test/runtests.py | 2 +- test/test_functions.py | 9 + test/test_mpfr.py | 290 +++++++++++++++++++++- test/test_mpfr.txt | 540 ----------------------------------------- 4 files changed, 297 insertions(+), 544 deletions(-) delete mode 100644 test/test_mpfr.txt diff --git a/test/runtests.py b/test/runtests.py index 9da87b5b..6141306e 100644 --- a/test/runtests.py +++ b/test/runtests.py @@ -26,7 +26,7 @@ mpz_doctests = ["test_mpz.txt"] -mpfr_doctests = ["test_mpfr.txt", "test_mpfr_trig.txt"] +mpfr_doctests = ["test_mpfr_trig.txt"] gmpy2_tests = [os.path.basename(i) for i in glob.glob(os.path.join(test_dir, diff --git a/test/test_functions.py b/test/test_functions.py index 987e2000..75aa8a6a 100644 --- a/test/test_functions.py +++ b/test/test_functions.py @@ -514,3 +514,12 @@ def test_sign(): assert sign(mpq(0,5)) == 0 pytest.raises(TypeError, lambda: sign('str')) + + a = mpfr("12.34") + + assert sign(-1.5) == -1 + assert sign(a) == 1 + assert sign(mpfr(0)) == 0 + assert sign(mpfr('inf')) == 1 + assert sign(mpfr('-inf')) == -1 + assert sign(mpfr('nan')) == 0 diff --git a/test/test_mpfr.py b/test/test_mpfr.py index b7020182..6573544d 100644 --- a/test/test_mpfr.py +++ b/test/test_mpfr.py @@ -1,4 +1,5 @@ import math +import pickle import sys from decimal import Decimal from fractions import Fraction @@ -9,9 +10,9 @@ from supportclasses import a, b, c, d, q, r, z import gmpy2 -from gmpy2 import (cmp, cmp_abs, from_binary, gamma_inc, inf, is_nan, mpc, - mpfr, mpfr_grandom, mpfr_nrandom, mpq, mpz, nan, - random_state, to_binary, xmpz, zero) +from gmpy2 import (cmp, cmp_abs, from_binary, gamma_inc, get_context, inf, + is_nan, mpc, mpfr, mpfr_grandom, mpfr_nrandom, mpq, mpz, + nan, random_state, to_binary, xmpz, zero) def test_mpfr_gamma_inc(): @@ -365,6 +366,45 @@ def test_mpfr_not(): assert not mpfr(1) is False +def test_mpfr_add(): + a = mpfr("12.34") + b = mpfr("45.67") + + assert a+1 == mpfr('13.34') + assert a+1.0 == mpfr('13.34') + assert a+mpz(1) == mpfr('13.34') + assert a+mpq(1,1) == mpfr('13.34') + assert 1+a == mpfr('13.34') + assert 1.0+a == mpfr('13.34') + assert mpz(1)+a == mpfr('13.34') + assert mpq(1,1)+a == mpfr('13.34') + assert a+b == mpfr('58.010000000000005') + assert a+0 == mpfr('12.34') + assert 0+a == mpfr('12.34') + assert b+a == mpfr('58.010000000000005') + + pytest.raises(TypeError, lambda: a+'b') + pytest.raises(TypeError, lambda: 'b'+a) + + assert a == 12.34 + assert b == 45.67 + assert a+b == 12.34+45.67 + + assert a + float('Inf') == mpfr('inf') + assert float('Inf') + a == mpfr('inf') + assert a + float('-Inf') == mpfr('-inf') + assert float('-Inf') + a == mpfr('-inf') + assert is_nan(a + float('nan')) + assert is_nan(float('nan') + a) + + assert a + mpfr('Inf') == mpfr('inf') + assert mpfr('Inf') + a == mpfr('inf') + assert a + mpfr('-Inf') == mpfr('-inf') + assert mpfr('-Inf') + a == mpfr('-inf') + assert is_nan(a + mpfr('nan')) + assert is_nan(mpfr('nan') + a) + + def test_mpfr_sub(): assert mpfr(10) - 1 == mpfr('9.0') assert 10 - mpfr(1) == mpfr('9.0') @@ -383,6 +423,35 @@ def test_mpfr_sub(): assert mpfr(10) - q == mpfr('8.5') assert mpfr(10) - r == mpfr('8.5') + a = mpfr("12.34") + b = mpfr("45.67") + + assert a-1 == mpfr('11.34') + assert a-1.0 == mpfr('11.34') + assert a-(-1) == mpfr('13.34') + assert a-(-1.0) == mpfr('13.34') + assert a-b == mpfr('-33.329999999999998') + assert b-a == mpfr('33.329999999999998') + + pytest.raises(TypeError, lambda: a-'b') + pytest.raises(TypeError, lambda: 'b'-a) + + assert a-b == 12.34-45.67 + + assert a - float('Inf') == mpfr('-inf') + assert float('Inf') - a == mpfr('inf') + assert a - float('-Inf') == mpfr('inf') + assert float('-Inf') - a == mpfr('-inf') + assert is_nan(a - float('nan')) + assert is_nan(float('nan') - a) + + assert a - mpfr('Inf') == mpfr('-inf') + assert mpfr('Inf') - a == mpfr('inf') + assert a - mpfr('-Inf') == mpfr('inf') + assert mpfr('-Inf') - a == mpfr('-inf') + assert is_nan(a - mpfr('nan')) + assert is_nan(mpfr('nan') - a) + def test_mpfr_mul(): c = 12345678901234567890 @@ -407,6 +476,52 @@ def test_mpfr_mul(): pytest.raises(TypeError, lambda: mpfr(10) * 'a') pytest.raises(TypeError, lambda: 'a' * mpfr(10)) + a = mpfr("12.34") + b = mpfr("45.67") + + assert a*b == mpfr('563.56780000000003') + assert a*0 == mpfr('0.0') + assert a*0.0 == mpfr('0.0') + assert a*1 == mpfr('12.34') + assert a*1.0 == mpfr('12.34') + assert a*(-1.0) == mpfr('-12.34') + assert 0*a == mpfr('0.0') + assert 0.0*a == mpfr('0.0') + assert 1*a == mpfr('12.34') + assert 1.0*a == mpfr('12.34') + assert a*b == mpfr('563.56780000000003') + assert a*b == 12.34*45.67 + + assert a * float('Inf') == mpfr('inf') + assert float('Inf') * a == mpfr('inf') + assert a * float('-Inf') == mpfr('-inf') + assert float('-Inf') * a == mpfr('-inf') + assert -a * float('Inf') == mpfr('-inf') + assert float('Inf') * -a == mpfr('-inf') + assert -a * float('-Inf') == mpfr('inf') + assert float('-Inf') * -a == mpfr('inf') + assert is_nan(a * float('nan')) + assert is_nan(float('nan') * a) + assert is_nan(mpfr(0) * float('Inf')) + assert is_nan(mpfr(0) * float('-Inf')) + assert is_nan(float('Inf') * mpfr(0)) + assert is_nan(float('-Inf') * mpfr(0)) + + assert a * mpfr('Inf') == mpfr('inf') + assert mpfr('Inf') * a == mpfr('inf') + assert a * mpfr('-Inf') == mpfr('-inf') + assert mpfr('-Inf') * a == mpfr('-inf') + assert -a * mpfr('Inf') == mpfr('-inf') + assert mpfr('Inf') * -a == mpfr('-inf') + assert -a * mpfr('-Inf') == mpfr('inf') + assert mpfr('-Inf') * -a == mpfr('inf') + assert is_nan(a * mpfr('nan')) + assert is_nan(mpfr('nan') * a) + assert is_nan(mpz(0) * mpfr('Inf')) + assert is_nan(mpz(0) * mpfr('-Inf')) + assert is_nan(mpfr('Inf') * mpfr(0)) + assert is_nan(mpfr('-Inf') * mpfr(0)) + def test_mpfr_divmod(): pytest.raises(TypeError, lambda: divmod(mpfr(1),'a')) @@ -437,6 +552,52 @@ def test_mpfr_divmod(): assert divmod(mpfr(111), mpfr(-222)) == (mpfr('-1.0'), mpfr('-111.0')) + a = mpfr("12.34") + b = mpfr("45.67") + + assert divmod(12.34, 45.67) == (0.0, 12.34) + assert divmod(a,b) == (mpfr('0.0'), mpfr('12.34')) + assert divmod(b,a) == (mpfr('3.0'), mpfr('8.6500000000000021')) + assert divmod(45.67,12.34) == divmod(b,a) + + assert divmod(a, float('Inf')) == (mpfr('0.0'), mpfr('12.34')) + assert divmod(a, float('-Inf')) == (mpfr('-1.0'), mpfr('-inf')) + assert divmod(-a, float('Inf')) == (mpfr('-1.0'), mpfr('inf')) + assert divmod(-a, float('-Inf')) == (mpfr('0.0'), mpfr('-12.34')) + assert all(map(is_nan, divmod(a, float('nan')))) + assert all(map(is_nan, divmod(-a, float('nan')))) + assert divmod(mpfr(0), float('Inf')) == (mpfr('0.0'), mpfr('0.0')) + assert divmod(mpfr(0), float('-Inf')) == (mpfr('-0.0'), mpfr('-0.0')) + assert divmod(mpfr(0), float('nan')) + assert all(map(is_nan, divmod(float('Inf'), a))) + assert all(map(is_nan, divmod(float('-Inf'), a))) + assert all(map(is_nan, divmod(float('Inf'), -a))) + assert all(map(is_nan, divmod(float('-Inf'), -a))) + assert all(map(is_nan, divmod(float('nan'), a))) + assert all(map(is_nan, divmod(float('nan'), -a))) + assert all(map(is_nan, divmod(float('Inf'), mpfr(0)))) + assert all(map(is_nan, divmod(float('-Inf'), mpfr(0)))) + assert all(map(is_nan, divmod(float('nan'), mpfr(0)))) + + assert divmod(a, mpfr('Inf')) == (mpfr('0.0'), mpfr('12.34')) + assert divmod(a, mpfr('-Inf')) == (mpfr('-1.0'), mpfr('-inf')) + assert divmod(-a, mpfr('Inf')) == (mpfr('-1.0'), mpfr('inf')) + assert divmod(-a, mpfr('-Inf')) == (mpfr('0.0'), mpfr('-12.34')) + assert all(map(is_nan, divmod(a, mpfr('nan')))) + assert all(map(is_nan, divmod(-a, mpfr('nan')))) + assert divmod(mpfr(0), mpfr('Inf')) == (mpfr('0.0'), mpfr('0.0')) + assert divmod(mpfr(0), mpfr('-Inf')) == (mpfr('-0.0'), mpfr('-0.0')) + assert divmod(mpfr(0), mpfr('nan')) + assert all(map(is_nan, divmod(mpfr('Inf'), a))) + assert all(map(is_nan, divmod(mpfr('-Inf'), a))) + assert all(map(is_nan, divmod(mpfr('Inf'), -a))) + assert all(map(is_nan, divmod(mpfr('-Inf'), -a))) + assert all(map(is_nan, divmod(mpfr('nan'), a))) + assert all(map(is_nan, divmod(mpfr('nan'), -a))) + assert all(map(is_nan, divmod(mpfr('Inf'), mpfr(0)))) + assert all(map(is_nan, divmod(mpfr('-Inf'), mpfr(0)))) + assert all(map(is_nan, divmod(mpfr('nan'), mpfr(0)))) + def test_mpfr_floordiv(): ctx = gmpy2.get_context() @@ -475,11 +636,119 @@ def test_mpfr_floordiv(): pytest.raises(TypeError, lambda: r // c2) pytest.raises(TypeError, lambda: r // 'not') + a = mpfr("12.34") + b = mpfr("45.67") + + assert a//b == mpfr('0.0') + assert b//a == mpfr('3.0') + + +def test_mpfr_truediv(): + a = mpfr("12.34") + b = mpfr("45.67") + + assert a/b == mpfr('0.27019925552879348') + assert gmpy2.div(a, b) == mpfr('0.27019925552879348') + assert get_context().div(a, b) == mpfr('0.27019925552879348') + assert b/a == mpfr('3.7009724473257699') + assert a/b == 12.34/45.67 + assert a/0 == mpfr('inf') + assert a/(-0.0) == mpfr('-inf') + assert a/b == 12.34/45.67 + assert mpfr(10) / z == mpfr('5.0') + assert mpfr(10) / q == mpfr('6.666666666666667') + assert mpfr(10) / r == mpfr('6.666666666666667') + assert b / mpc(4, 4) == mpc('5.7087500000000002-5.7087500000000002j') + assert get_context().div(b, mpc(4, 4)) == mpc('5.7087500000000002-5.7087500000000002j') + + ans = b / mpc(0, 0) + + assert ans.real == mpfr('inf') and is_nan(ans.imag) + + ans = get_context().div(b, mpc(0, 0)) + + assert ans.real == mpfr('inf') and is_nan(ans.imag) + + pytest.raises(TypeError, lambda: b / 'str') + pytest.raises(TypeError, lambda: get_context().div(b, 'str')) + + assert a / float('Inf') == mpfr('0.0') + assert -a / float('Inf') == mpfr('-0.0') + assert float('Inf') / a == mpfr('inf') + assert float('Inf') / -a == mpfr('-inf') + assert a / float('-Inf') == mpfr('-0.0') + assert -a / float('-Inf') == mpfr('0.0') + assert float('-Inf') / a == mpfr('-inf') + assert float('-Inf') / -a == mpfr('inf') + assert is_nan(a / float('nan')) + assert is_nan(float('nan') / a) + assert is_nan(float('nan') / mpfr(0)) + assert is_nan(float('nan') / mpfr(0)) + + assert a / mpfr('Inf') == mpfr('0.0') + assert -a / mpfr('Inf') == mpfr('-0.0') + assert mpfr('Inf') / a == mpfr('inf') + assert mpfr('Inf') / -a == mpfr('-inf') + assert a / mpfr('-Inf') == mpfr('-0.0') + assert -a / mpfr('-Inf') == mpfr('0.0') + assert mpfr('-Inf') / a == mpfr('-inf') + assert mpfr('-Inf') / -a == mpfr('inf') + assert is_nan(a / mpfr('nan')) + assert is_nan(mpfr('nan') / a) + assert is_nan(mpfr('nan') / mpfr(0)) + assert is_nan(mpfr('nan') / mpfr(0)) + def test_mpfr_mod(): r = mpfr('0.0') % mpfr('-1.0') assert r.is_zero() and r.is_signed() + a = mpfr("12.34") + b = mpfr("45.67") + + assert a % 1 == mpfr('0.33999999999999986') + assert 12.34 % 1 == 0.33999999999999986 + assert a % z == mpfr('0.33999999999999986') + assert is_nan(b % 0) + assert is_nan(b % mpz(0)) + assert is_nan(get_context().mod(b, 0)) + assert is_nan(get_context().mod(b, mpz(0))) + assert is_nan(b % mpfr(0)) + assert is_nan(get_context().mod(b, mpfr(0))) + + get_context().trap_divzero = True + + pytest.raises(gmpy2.DivisionByZeroError, lambda: b % 0) + pytest.raises(gmpy2.DivisionByZeroError, lambda: b % mpz(0)) + pytest.raises(gmpy2.DivisionByZeroError, lambda: get_context().mod(b, 0)) + pytest.raises(gmpy2.DivisionByZeroError, lambda: get_context().mod(b, mpz(0))) + pytest.raises(gmpy2.DivisionByZeroError, lambda: b % mpfr(0)) + pytest.raises(gmpy2.DivisionByZeroError, lambda: get_context().mod(b, mpfr(0))) + + get_context().trap_divzero = False + + pytest.raises(TypeError, lambda: b % 'str') + pytest.raises(TypeError, lambda: get_context().mod(b,'str')) + pytest.raises(TypeError, lambda: b % mpc(3, 5)) + + assert is_nan(mpfr('nan') % a) + assert is_nan(a % mpfr('nan')) + assert is_nan(mpfr('inf') % a) + assert a % mpfr('inf') == mpfr('12.34') + + get_context().trap_invalid = True + + pytest.raises(gmpy2.InvalidOperationError, lambda: mpfr('nan') % a) + pytest.raises(gmpy2.InvalidOperationError, lambda: a % mpfr('nan')) + pytest.raises(gmpy2.InvalidOperationError, lambda: mpfr('inf') % a) + pytest.raises(gmpy2.InvalidOperationError, lambda: a % mpfr('inf')) + + get_context().trap_invalid = False + + pytest.raises(TypeError, lambda: get_context().mod(a, b, 5)) + + assert get_context().mod(a, -mpfr('inf')) == mpfr('-inf') + def test_mpfr_pow(): r1, r2 = mpfr(5.0), mpfr(2.5) @@ -573,12 +842,27 @@ def test_mpfr_as_simple_fraction(): def test_mpfr_real_imag(): r = mpfr(4.55) + a = mpfr('12.34') assert r.imag == mpfr('0.0') assert r.real == mpfr('4.5499999999999998') + assert a.real == mpfr('12.34') + assert a.imag == mpfr('0.0') def test_mpfr_conjugate(): r = mpfr(4.55) + a = mpfr('12.34') assert r.conjugate() == r + assert a.conjugate() == a + + +def test_mpfr_pickle(): + a = mpfr('12.34') + + assert pickle.loads(pickle.dumps(a)) == a + assert pickle.loads(pickle.dumps(mpfr("inf"))) == mpfr('inf') + assert pickle.loads(pickle.dumps(mpfr("-inf"))) == mpfr('-inf') + assert is_nan(pickle.loads(pickle.dumps(mpfr("nan")))) + assert pickle.loads(pickle.dumps(mpfr(0))) == mpfr('0.0') diff --git a/test/test_mpfr.txt b/test/test_mpfr.txt deleted file mode 100644 index 05477c41..00000000 --- a/test/test_mpfr.txt +++ /dev/null @@ -1,540 +0,0 @@ -MPFR Functionality -================== - -Testing of mpfr functionality is split into multiple files. - ->>> import gmpy2 ->>> from gmpy2 import mpz, mpq, mpfr, mpc, get_context ->>> from supportclasses import * ->>> a = mpfr("12.34") ->>> b = mpfr("45.67") ->>> c = 12345678901234567890 - -Test elementary operations -========================== - -Test addition -------------- - ->>> a+1 -mpfr('13.34') ->>> a+1.0 -mpfr('13.34') ->>> a+mpz(1) -mpfr('13.34') ->>> a+mpq(1,1) -mpfr('13.34') ->>> 1+a -mpfr('13.34') ->>> 1.0+a -mpfr('13.34') ->>> mpz(1)+a -mpfr('13.34') ->>> mpq(1,1)+a -mpfr('13.34') ->>> a+b -mpfr('58.010000000000005') ->>> a+0 -mpfr('12.34') ->>> 0+a -mpfr('12.34') ->>> b+a -mpfr('58.010000000000005') ->>> a+'b' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for +: 'mpfr' and 'str' ->>> 'b'+a -Traceback (most recent call last): - File "", line 1, in -TypeError: Can't convert 'mpfr' object to str implicitly ->>> a == 12.34 -True ->>> b == 45.67 -True ->>> a+b == 12.34+45.67 -True - -Test subtraction ----------------- - ->>> a-1 -mpfr('11.34') ->>> a-1.0 -mpfr('11.34') ->>> a-(-1) -mpfr('13.34') ->>> a-(-1.0) -mpfr('13.34') ->>> a-b -mpfr('-33.329999999999998') ->>> b-a -mpfr('33.329999999999998') ->>> a-'b' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for -: 'mpfr' and 'str' ->>> 'b'-a -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for -: 'str' and 'mpfr' ->>> a-b==12.34-45.67 -True - -Test multiplication -------------------- - ->>> a*b -mpfr('563.56780000000003') ->>> a*0 -mpfr('0.0') ->>> a*0.0 -mpfr('0.0') ->>> a*1 -mpfr('12.34') ->>> a*1.0 -mpfr('12.34') ->>> a*(-1.0) -mpfr('-12.34') ->>> 0*a -mpfr('0.0') ->>> 0.0*a -mpfr('0.0') ->>> 1*a -mpfr('12.34') ->>> 1.0*a -mpfr('12.34') ->>> a*b -mpfr('563.56780000000003') ->>> a*b==12.34*45.67 -True - -Test division -------------- - ->>> a//b -mpfr('0.0') ->>> a/b -mpfr('0.27019925552879348') ->>> gmpy2.div(a, b) -mpfr('0.27019925552879348') ->>> get_context().div(a, b) -mpfr('0.27019925552879348') ->>> b//a -mpfr('3.0') ->>> b/a -mpfr('3.7009724473257699') ->>> a/b==12.34/45.67 -True ->>> a/0 -mpfr('inf') ->>> a/(-0.0) -mpfr('-inf') ->>> a/b==12.34/45.67 -True ->>> mpfr(10) / z -mpfr('5.0') ->>> mpfr(10) / q -mpfr('6.666666666666667') ->>> mpfr(10) / r -mpfr('6.666666666666667') ->>> b / mpc(4, 4) -mpc('5.7087500000000002-5.7087500000000002j') ->>> get_context().div(b, mpc(4, 4)) -mpc('5.7087500000000002-5.7087500000000002j') ->>> b / mpc(0, 0) -mpc('inf+nanj') ->>> get_context().div(b, mpc(0, 0)) -mpc('inf+nanj') ->>> b / 'str' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for /: 'mpfr' and 'str' ->>> get_context().div(b, 'str') -Traceback (most recent call last): - File "", line 1, in -TypeError: div() argument type not supported ->>> 1 -1 - - -Test modulo ------------ - ->>> a % 1 -mpfr('0.33999999999999986') ->>> 12.34 % 1 -0.33999999999999986 ->>> a % z -mpfr('0.33999999999999986') ->>> b % 0 -mpfr('nan') ->>> b % mpz(0) -mpfr('nan') ->>> get_context().mod(b, 0) -mpfr('nan') ->>> get_context().mod(b, mpz(0)) -mpfr('nan') ->>> b % mpfr(0) -mpfr('nan') ->>> get_context().mod(b, mpfr(0)) -mpfr('nan') ->>> get_context().trap_divzero = True ->>> b % 0 -Traceback (most recent call last): - File "", line 1, in -gmpy2.DivisionByZeroError: mod() modulo by zero ->>> b % mpz(0) -Traceback (most recent call last): - File "", line 1, in -gmpy2.DivisionByZeroError: mod() modulo by zero ->>> get_context().mod(b, 0) -Traceback (most recent call last): - File "", line 1, in -gmpy2.DivisionByZeroError: mod() modulo by zero ->>> get_context().mod(b, mpz(0)) -Traceback (most recent call last): - File "", line 1, in -gmpy2.DivisionByZeroError: mod() modulo by zero ->>> b % mpfr(0) -Traceback (most recent call last): - File "", line 1, in -gmpy2.DivisionByZeroError: mod() modulo by zero ->>> get_context().mod(b, mpfr(0)) -Traceback (most recent call last): - File "", line 1, in -gmpy2.DivisionByZeroError: mod() modulo by zero ->>> get_context().trap_divzero = False ->>> b % 'str' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for %: 'mpfr' and 'str' ->>> get_context().mod(b,'str') -Traceback (most recent call last): - File "", line 1, in -TypeError: mod() argument type not supported ->>> b % mpc(3, 5) -Traceback (most recent call last): - File "", line 1, in -TypeError: can't take mod of complex number ->>> mpfr('nan') % a -mpfr('nan') ->>> a % mpfr('nan') -mpfr('nan') ->>> mpfr('inf') % a -mpfr('nan') ->>> a % mpfr('inf') -mpfr('12.34') ->>> get_context().trap_invalid = True ->>> mpfr('nan') % a -Traceback (most recent call last): - File "", line 1, in -gmpy2.InvalidOperationError: invalid operation ->>> a % mpfr('nan') -Traceback (most recent call last): - File "", line 1, in -gmpy2.InvalidOperationError: invalid operation ->>> mpfr('inf') % a -Traceback (most recent call last): - File "", line 1, in -gmpy2.InvalidOperationError: mod() invalid operation ->>> a % mpfr('inf') -Traceback (most recent call last): - File "", line 1, in -gmpy2.InvalidOperationError: mod() invalid operation ->>> get_context().trap_invalid = False ->>> get_context().mod(a, b, 5) -Traceback (most recent call last): - File "", line 1, in -TypeError: mod() requires 2 arguments ->>> 1 -1 ->>> get_context().mod(a, -mpfr('inf')) -mpfr('-inf') - -Test divmod ------------ - ->>> divmod(12.34, 45.67) -(0.0, 12.34) ->>> divmod(a,b) -(mpfr('0.0'), mpfr('12.34')) ->>> divmod(b,a) -(mpfr('3.0'), mpfr('8.6500000000000021')) ->>> divmod(45.67,12.34)==divmod(b,a) -True - - -Test pickle ------------ - ->>> import pickle ->>> pickle.loads(pickle.dumps(a)) -mpfr('12.34') ->>> pickle.loads(pickle.dumps(mpfr("inf"))) -mpfr('inf') ->>> pickle.loads(pickle.dumps(mpfr("-inf"))) -mpfr('-inf') ->>> pickle.loads(pickle.dumps(mpfr("nan"))) -mpfr('nan') ->>> pickle.loads(pickle.dumps(mpfr(0))) -mpfr('0.0') - - -Test operations involving NaN/Inf ---------------------------------- - ->>> a + float('Inf') -mpfr('inf') ->>> float('Inf') + a -mpfr('inf') ->>> a + float('-Inf') -mpfr('-inf') ->>> float('-Inf') + a -mpfr('-inf') ->>> a + float('nan') -mpfr('nan') ->>> float('nan') + a -mpfr('nan') ->>> a - float('Inf') -mpfr('-inf') ->>> float('Inf') - a -mpfr('inf') ->>> a - float('-Inf') -mpfr('inf') ->>> float('-Inf') - a -mpfr('-inf') ->>> a - float('nan') -mpfr('nan') ->>> float('nan') - a -mpfr('nan') ->>> a * float('Inf') -mpfr('inf') ->>> float('Inf') * a -mpfr('inf') ->>> a * float('-Inf') -mpfr('-inf') ->>> float('-Inf') * a -mpfr('-inf') ->>> -a * float('Inf') -mpfr('-inf') ->>> float('Inf') * -a -mpfr('-inf') ->>> -a * float('-Inf') -mpfr('inf') ->>> float('-Inf') * -a -mpfr('inf') ->>> a * float('nan') -mpfr('nan') ->>> float('nan') * a -mpfr('nan') ->>> mpfr(0) * float('Inf') -mpfr('nan') ->>> mpfr(0) * float('-Inf') -mpfr('nan') ->>> float('Inf') * mpfr(0) -mpfr('nan') ->>> float('-Inf') * mpfr(0) -mpfr('nan') ->>> a / float('Inf') -mpfr('0.0') ->>> -a / float('Inf') -mpfr('-0.0') ->>> float('Inf') / a -mpfr('inf') ->>> float('Inf') / -a -mpfr('-inf') ->>> a / float('-Inf') -mpfr('-0.0') ->>> -a / float('-Inf') -mpfr('0.0') ->>> float('-Inf') / a -mpfr('-inf') ->>> float('-Inf') / -a -mpfr('inf') ->>> a / float('nan') -mpfr('nan') ->>> float('nan') / a -mpfr('nan') ->>> float('nan') / mpfr(0) -mpfr('nan') ->>> float('nan') / mpfr(0) -mpfr('nan') - ->>> a + mpfr('Inf') -mpfr('inf') ->>> mpfr('Inf') + a -mpfr('inf') ->>> a + mpfr('-Inf') -mpfr('-inf') ->>> mpfr('-Inf') + a -mpfr('-inf') ->>> a + mpfr('nan') -mpfr('nan') ->>> mpfr('nan') + a -mpfr('nan') ->>> a - mpfr('Inf') -mpfr('-inf') ->>> mpfr('Inf') - a -mpfr('inf') ->>> a - mpfr('-Inf') -mpfr('inf') ->>> mpfr('-Inf') - a -mpfr('-inf') ->>> a - mpfr('nan') -mpfr('nan') ->>> mpfr('nan') - a -mpfr('nan') ->>> a * mpfr('Inf') -mpfr('inf') ->>> mpfr('Inf') * a -mpfr('inf') ->>> a * mpfr('-Inf') -mpfr('-inf') ->>> mpfr('-Inf') * a -mpfr('-inf') ->>> -a * mpfr('Inf') -mpfr('-inf') ->>> mpfr('Inf') * -a -mpfr('-inf') ->>> -a * mpfr('-Inf') -mpfr('inf') ->>> mpfr('-Inf') * -a -mpfr('inf') ->>> a * mpfr('nan') -mpfr('nan') ->>> mpfr('nan') * a -mpfr('nan') ->>> mpz(0) * mpfr('Inf') -mpfr('nan') ->>> mpz(0) * mpfr('-Inf') -mpfr('nan') ->>> mpfr('Inf') * mpfr(0) -mpfr('nan') ->>> mpfr('-Inf') * mpfr(0) -mpfr('nan') ->>> a / mpfr('Inf') -mpfr('0.0') ->>> -a / mpfr('Inf') -mpfr('-0.0') ->>> mpfr('Inf') / a -mpfr('inf') ->>> mpfr('Inf') / -a -mpfr('-inf') ->>> a / mpfr('-Inf') -mpfr('-0.0') ->>> -a / mpfr('-Inf') -mpfr('0.0') ->>> mpfr('-Inf') / a -mpfr('-inf') ->>> mpfr('-Inf') / -a -mpfr('inf') ->>> a / mpfr('nan') -mpfr('nan') ->>> mpfr('nan') / a -mpfr('nan') ->>> mpfr('nan') / mpfr(0) -mpfr('nan') ->>> mpfr('nan') / mpfr(0) -mpfr('nan') - ->>> divmod(a, float('Inf')) -(mpfr('0.0'), mpfr('12.34')) ->>> divmod(a, float('-Inf')) -(mpfr('-1.0'), mpfr('-inf')) ->>> divmod(-a, float('Inf')) -(mpfr('-1.0'), mpfr('inf')) ->>> divmod(-a, float('-Inf')) -(mpfr('0.0'), mpfr('-12.34')) ->>> divmod(a, float('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(-a, float('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr(0), float('Inf')) -(mpfr('0.0'), mpfr('0.0')) ->>> divmod(mpfr(0), float('-Inf')) -(mpfr('-0.0'), mpfr('-0.0')) ->>> divmod(mpfr(0), float('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('-Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('-Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('nan'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('nan'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('Inf'), mpfr(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('-Inf'), mpfr(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(float('nan'), mpfr(0)) -(mpfr('nan'), mpfr('nan')) - ->>> divmod(a, mpfr('Inf')) -(mpfr('0.0'), mpfr('12.34')) ->>> divmod(a, mpfr('-Inf')) -(mpfr('-1.0'), mpfr('-inf')) ->>> divmod(-a, mpfr('Inf')) -(mpfr('-1.0'), mpfr('inf')) ->>> divmod(-a, mpfr('-Inf')) -(mpfr('0.0'), mpfr('-12.34')) ->>> divmod(a, mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(-a, mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr(0), mpfr('Inf')) -(mpfr('0.0'), mpfr('0.0')) ->>> divmod(mpfr(0), mpfr('-Inf')) -(mpfr('-0.0'), mpfr('-0.0')) ->>> divmod(mpfr(0), mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), mpfr(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), mpfr(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), mpfr(0)) -(mpfr('nan'), mpfr('nan')) - -Test Number Protocol --------------------- - ->>> a.real -mpfr('12.34') ->>> a.imag -mpfr('0.0') ->>> a.conjugate() -mpfr('12.34') - -Test sign function ------------------- - ->>> gmpy2.sign(-1.5) --1 ->>> gmpy2.sign(a) -1 ->>> gmpy2.sign(mpfr(0)) -0 ->>> gmpy2.sign(mpfr('inf')) -1 ->>> gmpy2.sign(mpfr('-inf')) --1 ->>> gmpy2.sign(mpfr('nan')) -0 - From 69661f38164f6a388cd7f01b0ca86467ee6b2a15 Mon Sep 17 00:00:00 2001 From: Sergey B Kirpichev Date: Sun, 19 Nov 2023 15:04:15 +0300 Subject: [PATCH 5/9] Port test/test_mpz.txt to pytest framework --- test/runtests.py | 6 +- test/test_functions.py | 9 + test/test_mpz.py | 349 ++++++++++++++++++++++- test/test_mpz.txt | 626 ----------------------------------------- 4 files changed, 356 insertions(+), 634 deletions(-) delete mode 100644 test/test_mpz.txt diff --git a/test/runtests.py b/test/runtests.py index 6141306e..85ee1f52 100644 --- a/test/runtests.py +++ b/test/runtests.py @@ -24,8 +24,6 @@ print(" Complex library: {0}".format(gmpy2.mpc_version())) print() -mpz_doctests = ["test_mpz.txt"] - mpfr_doctests = ["test_mpfr_trig.txt"] gmpy2_tests = [os.path.basename(i) @@ -35,9 +33,7 @@ failed = 0 attempted = 0 -all_doctests = gmpy2_tests + mpz_doctests - -all_doctests += mpfr_doctests +all_doctests = gmpy2_tests + mpfr_doctests for test in sorted(all_doctests): result = doctest.testfile(test, globs=globals(), diff --git a/test/test_functions.py b/test/test_functions.py index 75aa8a6a..d1d30b16 100644 --- a/test/test_functions.py +++ b/test/test_functions.py @@ -523,3 +523,12 @@ def test_sign(): assert sign(mpfr('inf')) == 1 assert sign(mpfr('-inf')) == -1 assert sign(mpfr('nan')) == 0 + + a = mpz(123) + b = mpz(456) + + assert sign(b-a) == 1 + assert sign(b-b) == 0 + assert sign(a-b) == -1 + assert sign(a) == 1 + assert sign(-a) == -1 diff --git a/test/test_mpz.py b/test/test_mpz.py index b6f19caf..69fb0466 100644 --- a/test/test_mpz.py +++ b/test/test_mpz.py @@ -9,9 +9,9 @@ from supportclasses import a, b, c, d, q, z import gmpy2 -from gmpy2 import (cmp, cmp_abs, from_binary, mp_version, mpc, mpfr, mpq, mpz, - mpz_random, mpz_rrandomb, mpz_urandomb, pack, random_state, - to_binary, unpack, xmpz) +from gmpy2 import (cmp, cmp_abs, from_binary, is_nan, mp_version, mpc, mpfr, + mpq, mpz, mpz_random, mpz_rrandomb, mpz_urandomb, pack, + random_state, to_binary, unpack, xmpz) def test_mpz_to_bytes_interface(): @@ -320,6 +320,8 @@ def test_mpz_conversion(): raises(OverflowError, lambda: float(mpz(99**199))) assert mpz(xmpz(1)) == mpz(1) + assert int(mpz(-3)) == -3 + def test_mpz_create(): assert mpz() == mpz(0) @@ -435,6 +437,7 @@ def test_mpz_create(): @given(integers()) @example(0) +@example(-3) def test_mpz_conversion_bulk(n): assert int(mpz(n)) == n @@ -617,6 +620,7 @@ def test_mpz_abs(): b = abs(a) assert a is b + assert abs(-a) == a a = mpz(-123) b = abs(a) @@ -626,6 +630,34 @@ def test_mpz_abs(): assert a == mpz(-123) +def test_mpz_add(): + a = mpz(123) + b = mpz(456) + c = 12345678901234567890 + + assert a+1 == mpz(124) + assert a+(-1) == mpz(122) + assert 1+a == mpz(124) + assert (-1)+a == mpz(122) + assert a+b == mpz(579) + assert b+a == mpz(579) + + raises(TypeError, lambda: a+'b') + raises(TypeError, lambda: 'b'+a) + assert a+c == 12345678901234568013 + assert c+a == 12345678901234568013 + + assert a+True == mpz(124) + assert a+False == mpz(123) + + assert a + float('Inf') == mpfr('inf') + assert float('Inf') + a == mpfr('inf') + assert a + float('-Inf') == mpfr('-inf') + assert float('-Inf') + a == mpfr('-inf') + assert is_nan(a + float('nan')) + assert is_nan(float('nan') + a) + + def test_mpz_sub(): a, b = mpz(123), mpz(456) c = 12345678901234567890 @@ -661,6 +693,26 @@ def test_mpz_sub(): raises(TypeError, lambda: a-'b') raises(TypeError, lambda: 'b'-a) + assert a-1 == mpz(122) + assert a-(-1) == mpz(124) + assert 1-a == mpz(-122) + assert (-1)-a == mpz(-124) + assert a-b == mpz(-333) + assert b-a == mpz(333) + + raises(TypeError, lambda: a-'b') + raises(TypeError, lambda: 'b'-a) + + assert a-c == -12345678901234567767 + assert c-a == 12345678901234567767 + + assert a - float('Inf') == mpfr('-inf') + assert float('Inf') - a == mpfr('inf') + assert a - float('-Inf') == mpfr('inf') + assert float('-Inf') - a == mpfr('-inf') + assert is_nan(a - float('nan')) + assert is_nan(float('nan') - a) + def test_mpz_mul(): a = mpz(123) @@ -681,10 +733,43 @@ def test_mpz_mul(): raises(TypeError, lambda: ctx.mul(1)) raises(TypeError, lambda: ctx.mul(1,2,3)) + assert a*b == mpz(56088) + assert b*a == mpz(56088) + assert a*0 == mpz(0) + assert 0*a == mpz(0) + assert a*123 == mpz(15129) + assert 123*a == mpz(15129) + assert a*c == 1518518504851851850470 + assert c*a == 1518518504851851850470 + + a = mpz(3) + + assert a*'b' == 'bbb' + assert 'b'*a == 'bbb' + + assert a*False == mpz(0) + + assert a * float('Inf') == mpfr('inf') + assert float('Inf') * a == mpfr('inf') + assert a * float('-Inf') == mpfr('-inf') + assert float('-Inf') * a == mpfr('-inf') + assert -a * float('Inf') == mpfr('-inf') + assert float('Inf') * -a == mpfr('-inf') + assert -a * float('-Inf') == mpfr('inf') + assert float('-Inf') * -a == mpfr('inf') + assert is_nan(a * float('nan')) + assert is_nan(float('nan') * a) + assert is_nan(mpz(0) * float('Inf')) + assert is_nan(mpz(0) * float('-Inf')) + assert is_nan(float('Inf') * mpz(0)) + assert is_nan(float('-Inf') * mpz(0)) + def test_mpz_divmod(): a = mpz(123) b = mpz(456) + c = 12345678901234567890 + ctx = gmpy2.get_context() raises(TypeError, lambda: divmod(mpz(123),'a')) @@ -701,6 +786,60 @@ def test_mpz_divmod(): assert divmod(mpz(3), z) == (mpz(1), mpz(1)) assert divmod(z, mpz(3)) == (mpz(0), mpz(2)) + assert divmod(a,b) == (mpz(0), mpz(123)) + assert divmod(b,a) == (mpz(3), mpz(87)) + + raises(ZeroDivisionError, lambda: divmod(a,0)) + raises(ZeroDivisionError, lambda: divmod(a, mpz(0))) + raises(ZeroDivisionError, lambda: divmod(123, mpz(0))) + + assert divmod(b,123) == (mpz(3), mpz(87)) + assert divmod(a,c) == (mpz(0), mpz(123)) + assert divmod(a,int(c)) == (mpz(0), mpz(123)) + assert divmod(a*(c-1),c) == (122, 12345678901234567767) + assert divmod(a*(c-1),int(c)) == (122, 12345678901234567767) + assert divmod(a*(c-1),-c) == (mpz(-123), mpz(-123)) + assert divmod(a*(c-1),-int(c)) == (mpz(-123), mpz(-123)) + assert divmod(int(a*(c-1)),-int(c)) == (-123, -123) + + assert divmod(a, mpfr('Inf')) == (mpfr('0.0'), mpfr('123.0')) + assert divmod(a, mpfr('-Inf')) == (mpfr('-1.0'), mpfr('-inf')) + assert divmod(-a, mpfr('Inf')) == (mpfr('-1.0'), mpfr('inf')) + assert divmod(-a, mpfr('-Inf')) == (mpfr('0.0'), mpfr('-123.0')) + assert all(is_nan(_) for _ in divmod(a, mpfr('nan'))) + assert all(is_nan(_) for _ in divmod(-a, mpfr('nan'))) + assert divmod(mpz(0), mpfr('Inf')) == (mpfr('0.0'), mpfr('0.0')) + assert divmod(mpz(0), mpfr('-Inf')) == (mpfr('-0.0'), mpfr('-0.0')) + assert divmod(mpz(0), mpfr('nan')) + assert all(is_nan(_) for _ in divmod(mpfr('Inf'), a)) + assert all(is_nan(_) for _ in divmod(mpfr('-Inf'), a)) + assert all(is_nan(_) for _ in divmod(mpfr('Inf'), -a)) + assert all(is_nan(_) for _ in divmod(mpfr('-Inf'), -a)) + assert all(is_nan(_) for _ in divmod(mpfr('nan'), a)) + assert all(is_nan(_) for _ in divmod(mpfr('nan'), -a)) + assert all(is_nan(_) for _ in divmod(mpfr('Inf'), mpz(0))) + assert all(is_nan(_) for _ in divmod(mpfr('-Inf'), mpz(0))) + assert all(is_nan(_) for _ in divmod(mpfr('nan'), mpz(0))) + + assert divmod(a, mpfr('Inf')) == (mpfr('0.0'), mpfr('123.0')) + assert divmod(a, mpfr('-Inf')) == (mpfr('-1.0'), mpfr('-inf')) + assert divmod(-a, mpfr('Inf')) == (mpfr('-1.0'), mpfr('inf')) + assert divmod(-a, mpfr('-Inf')) == (mpfr('0.0'), mpfr('-123.0')) + assert all(is_nan(_) for _ in divmod(a, mpfr('nan'))) + assert all(is_nan(_) for _ in divmod(-a, mpfr('nan'))) + assert divmod(mpz(0), mpfr('Inf')) == (mpfr('0.0'), mpfr('0.0')) + assert divmod(mpz(0), mpfr('-Inf')) == (mpfr('-0.0'), mpfr('-0.0')) + assert divmod(mpz(0), mpfr('nan')) + assert all(is_nan(_) for _ in divmod(mpfr('Inf'), a)) + assert all(is_nan(_) for _ in divmod(mpfr('-Inf'), a)) + assert all(is_nan(_) for _ in divmod(mpfr('Inf'), -a)) + assert all(is_nan(_) for _ in divmod(mpfr('-Inf'), -a)) + assert all(is_nan(_) for _ in divmod(mpfr('nan'), a)) + assert all(is_nan(_) for _ in divmod(mpfr('nan'), -a)) + assert all(is_nan(_) for _ in divmod(mpfr('Inf'), mpz(0))) + assert all(is_nan(_) for _ in divmod(mpfr('-Inf'), mpz(0))) + assert all(is_nan(_) for _ in divmod(mpfr('nan'), mpz(0))) + def test_mpz_floordiv(): ctx = gmpy2.get_context() @@ -739,6 +878,100 @@ def test_mpz_floordiv(): raises(TypeError, lambda: a // c2) raises(TypeError, lambda: a // 'not') + a = mpz(123) + b = mpz(456) + c = 12345678901234567890 + + assert a//b == mpz(0) + assert b//a == mpz(3) + assert (a*b)//b == mpz(123) + assert (a*b)//a == mpz(456) + + raises(ZeroDivisionError, lambda: a//0) + + assert c//a == 100371373180768844 + assert a**10//c == mpz(64) + assert a // z == mpz(61) + + assert a//True == mpz(123) + + +def test_mpz_mod(): + a = mpz(123) + b = mpz(456) + c = 12345678901234567890 + ctx = gmpy2.get_context() + + assert a % b == mpz(123) + assert b % a == mpz(87) + assert gmpy2.mod(b, a) == mpz(87) + assert ctx.mod(b, a) == mpz(87) + assert a % z == mpz(1) + + raises(ZeroDivisionError, lambda: a % mpz(0)) + raises(ZeroDivisionError, lambda: a % 0) + raises(ZeroDivisionError, lambda: 14 % mpz(0)) + raises(ZeroDivisionError, lambda: gmpy2.mod(14, mpz(0))) + raises(ZeroDivisionError, lambda: gmpy2.mod(124, 0)) + raises(ZeroDivisionError, lambda: gmpy2.mod(b, mpz(0))) + raises(ZeroDivisionError, lambda: ctx.mod(b, mpz(0))) + raises(TypeError, lambda: gmpy2.mod(124, 'str')) + raises(TypeError, lambda: a % 'str') + + assert gmpy2.mod(124, mpz(5)) == mpz(4) + assert z % mpq(1,2) == mpq(0,1) + assert a % mpq(2,3) == mpq(1,3) + + +def test_mpz_truediv(): + a = mpz(123) + b = mpz(456) + c = 12345678901234567890 + ctx = gmpy2.get_context() + + assert a/b == mpfr('0.26973684210526316') + assert gmpy2.div(a, b) == mpfr('0.26973684210526316') + assert ctx.div(a, b) == mpfr('0.26973684210526316') + assert b/a == mpfr('3.7073170731707319') + + raises(ZeroDivisionError, lambda: a/0) + + assert a/0.0 == mpfr('inf') + assert a / z == mpfr('61.5') + + raises(TypeError, lambda: ctx.div(a, b, 5)) + raises(TypeError, lambda: ctx.div(a, 'str')) + raises(TypeError, lambda: a / 'str') + + with gmpy2.local_context(rational_division=True): + assert mpz(1)/mpz(2) == mpq(1, 2) + + assert a / float('Inf') == mpfr('0.0') + assert -a / float('Inf') == mpfr('-0.0') + assert float('Inf') / a == mpfr('inf') + assert float('Inf') / -a == mpfr('-inf') + assert a / float('-Inf') == mpfr('-0.0') + assert -a / float('-Inf') == mpfr('0.0') + assert float('-Inf') / a == mpfr('-inf') + assert float('-Inf') / -a == mpfr('inf') + assert is_nan(a / float('nan')) + assert is_nan(float('nan') / a) + assert is_nan(float('nan') / mpz(0)) + assert is_nan(float('nan') / mpz(0)) + + assert a / mpfr('Inf') == mpfr('0.0') + assert -a / mpfr('Inf') == mpfr('-0.0') + assert mpfr('Inf') / a == mpfr('inf') + assert mpfr('Inf') / -a == mpfr('-inf') + assert a / mpfr('-Inf') == mpfr('-0.0') + assert -a / mpfr('-Inf') == mpfr('0.0') + assert mpfr('-Inf') / a == mpfr('-inf') + assert mpfr('-Inf') / -a == mpfr('inf') + assert is_nan(a / mpfr('nan')) + assert is_nan(mpfr('nan') / a) + assert is_nan(mpfr('nan') / mpz(0)) + assert is_nan(mpfr('nan') / mpz(0)) + def test_mpz_pow(): z1, z2 = mpz(5), mpz(2) @@ -764,6 +997,12 @@ def test_mpz_pow(): raises(ValueError, lambda: pow(5, 2, 0)) raises(TypeError, lambda: ctx.pow(z1, 'invalid')) + a = mpz(123) + b = mpz(456) + + assert pow(a,10) == 792594609605189126649 + assert pow(a,7,b) == mpz(99) + def test_lucasu(): assert gmpy2.lucasu(2,4,1) == mpz(1) @@ -793,3 +1032,107 @@ def test_lucasu(): assert gmpy2.lucasv_mod(4,3,55,123456) == mpz(35788) assert gmpy2.lucasv_mod(4,3,56,123456) == mpz(107362) assert gmpy2.lucasv_mod(4,3,57,123456) == mpz(75172) + + +def test_mpz_attributes(): + a = mpz(123) + + assert a.numerator == mpz(123) + assert a.denominator == mpz(1) + + assert a.real == mpz(123) + assert a.imag == mpz(0) + + +def test_mpz_conjugate(): + a = mpz(123) + + assert a.conjugate() == a + + +def test_mpz_invert(): + a = mpz(123) + + assert ~a == mpz(-124) + + +def test_mpz_and(): + a = mpz(123) + b = mpz(456) + + assert a&b == mpz(72) + assert a&int(b) == mpz(72) + assert int(a)&b == mpz(72) + + raises(TypeError, lambda: a&mpq(1)) + + +def test_mpz_or(): + a = mpz(123) + b = mpz(456) + + assert a|b == mpz(507) + assert a|int(b) == mpz(507) + assert int(a)|b == mpz(507) + + raises(TypeError, lambda: a|mpq(1)) + + +def test_mpz_xor(): + a = mpz(123) + b = mpz(456) + + assert a^b == mpz(435) + assert a^int(b) == mpz(435) + assert int(a)^b == mpz(435) + + raises(TypeError, lambda: a^mpq(1)) + + +def test_mpz_lshift(): + a = mpz(123) + + assert a<<1 == mpz(246) + assert int(a)<>1 == mpz(61) + assert int(a)>>mpz(1) == mpz(61) + + raises(OverflowError, lambda: a>>-2) + + assert a>>0 == mpz(123) + + raises(TypeError, lambda: "a" >> a) + + +def test_mpz_index(): + a = mpz(123) + b = mpz(456) + + assert range(333)[a] == 123 + + raises(IndexError, lambda: range(333)[b]) + + +def test_mpz_seq(): + a = mpz(10) + + assert a[1] == 1 + assert a[-1] == 1 + assert a[-2] == 0 + assert a[0:2] == mpz(2) + assert a[0:3] == mpz(2) + assert a[0:3:-1] == mpz(0) + + raises(IndexError, lambda: a[111111111111111111111]) + raises(TypeError, lambda: a["spam"]) diff --git a/test/test_mpz.txt b/test/test_mpz.txt deleted file mode 100644 index 2abf5f3c..00000000 --- a/test/test_mpz.txt +++ /dev/null @@ -1,626 +0,0 @@ -MPZ Functionality -================= - -Testing of mpz functionality is split into multiple files. - - test_mpz.txt - Test basic functionality and stuff not covered anywhere else. - - test_mpz_functions.txt - Test mpz functions, including error messages. - - test_mpz_io.txt - Test input/output and formating. - - test_mpz_comp.txt - Test comparisons. - ->>> import gmpy2 as G ->>> from gmpy2 import mpz, mpq, mpfr, mpc ->>> from supportclasses import * ->>> from decimal import Decimal as D ->>> from fractions import Fraction as F ->>> a = mpz(123) ->>> b = mpz(456) ->>> c = 12345678901234567890 ->>> ctx = gmpy2.get_context() - -Test elementary operations -========================== - -Test addition -------------- - ->>> a+1 -mpz(124) ->>> a+(-1) -mpz(122) ->>> 1+a -mpz(124) ->>> (-1)+a -mpz(122) ->>> a+b -mpz(579) ->>> b+a -mpz(579) ->>> a+'b' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for +: 'mpz' and 'str' ->>> 'b'+a -Traceback (most recent call last): - File "", line 1, in -TypeError: ** message detail varies ** ->>> print(a+c) -12345678901234568013 ->>> print(c+a) -12345678901234568013 - - -Test subtraction ----------------- - ->>> a-1 -mpz(122) ->>> a-(-1) -mpz(124) ->>> 1-a -mpz(-122) ->>> (-1)-a -mpz(-124) ->>> a-b -mpz(-333) ->>> b-a -mpz(333) ->>> a-'b' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for -: 'mpz' and 'str' ->>> 'b'-a -Traceback (most recent call last): - File "", line 1, in -TypeError: ** message detail varies ** ->>> print(a-c) --12345678901234567767 ->>> print(c-a) -12345678901234567767 - -Test multiplication -------------------- - ->>> a*b -mpz(56088) ->>> b*a -mpz(56088) ->>> a*0 -mpz(0) ->>> 0*a -mpz(0) ->>> a*123 -mpz(15129) ->>> 123*a -mpz(15129) ->>> print(a*c) -1518518504851851850470 ->>> print(c*a) -1518518504851851850470 ->>> a*'b' -'bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb' ->>> 'b'*a -'bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb' - -Test division -------------- - ->>> a//b -mpz(0) ->>> a/b -mpfr('0.26973684210526316') ->>> gmpy2.div(a, b) -mpfr('0.26973684210526316') ->>> ctx.div(a, b) -mpfr('0.26973684210526316') ->>> b//a -mpz(3) ->>> b/a -mpfr('3.7073170731707319') ->>> (a*b)//b -mpz(123) ->>> (a*b)//a -mpz(456) ->>> a//0 -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> a/0 -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> a/0.0 -mpfr('inf') ->>> print(c//a) -100371373180768844 ->>> a**10//c -mpz(64) ->>> a / z -mpfr('61.5') ->>> a // z -mpz(61) ->>> ctx.div(a, b, 5) -Traceback (most recent call last): - File "", line 1, in -TypeError: div() requires 2 arguments. ->>> ctx.div(a, 'str') -Traceback (most recent call last): - File "", line 1, in -TypeError: div() argument type not supported ->>> a / 'str' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for /: 'mpz' and 'str' ->>> 1 -1 ->>> with gmpy2.local_context(rational_division=True): -... print(mpz(1)/mpz(2)) -... -1/2 - -Test modulo ------------ - ->>> a % b -mpz(123) ->>> b % a -mpz(87) ->>> gmpy2.mod(b, a) -mpz(87) ->>> ctx.mod(b, a) -mpz(87) ->>> a % z -mpz(1) ->>> divmod(a,b) -(mpz(0), mpz(123)) ->>> divmod(b,a) -(mpz(3), mpz(87)) ->>> a % mpz(0) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> divmod(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: division or modulo by zero ->>> divmod(a, mpz(0)) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> divmod(123, mpz(0)) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> a % 0 -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> 14 % mpz(0) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> gmpy2.mod(14, mpz(0)) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> gmpy2.mod(124, 0) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> gmpy2.mod(b, mpz(0)) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> ctx.mod(b, mpz(0)) -Traceback (most recent call last): - File "", line 1, in -ZeroDivisionError: division or modulo by zero ->>> gmpy2.mod(124, 'str') -Traceback (most recent call last): - File "", line 1, in -TypeError: mod() argument type not supported ->>> a % 'str' -Traceback (most recent call last): - File "", line 1, in -TypeError: unsupported operand type(s) for %: 'mpz' and 'str' ->>> gmpy2.mod(124, mpz(5)) -mpz(4) ->>> divmod(b,123) -(mpz(3), mpz(87)) ->>> divmod(a,c) -(mpz(0), mpz(123)) ->>> divmod(a,int(c)) -(mpz(0), mpz(123)) ->>> print("%s %s" % divmod(a*(c-1),c)) -122 12345678901234567767 ->>> print("%s %s" % divmod(a*(c-1),int(c))) -122 12345678901234567767 ->>> divmod(a*(c-1),-c) -(mpz(-123), mpz(-123)) ->>> divmod(a*(c-1),-int(c)) -(mpz(-123), mpz(-123)) ->>> print("%s %s" % divmod(int(a*(c-1)),-int(c))) --123 -123 ->>> z % mpq(1,2) -mpq(0,1) ->>> a % mpq(2,3) -mpq(1,3) - -Test miscellaneous ------------------- - ->>> a+True -mpz(124) ->>> a+False -mpz(123) ->>> a*False -mpz(0) ->>> a//True -mpz(123) ->>> abs(-a) == a -True ->>> print(pow(a,10)) -792594609605189126649 ->>> pow(a,7,b) -mpz(99) ->>> G.sign(b-a) -1 ->>> G.sign(b-b) -0 ->>> G.sign(a-b) --1 ->>> G.sign(a) -1 ->>> G.sign(-a) --1 ->>> z=b-b; G.sign(z) -0 - -Test mpz.__index__ ------------------- - ->>> range(333)[a] -123 ->>> range(333)[b] -Traceback (innermost last): - ... -IndexError: range object index out of range ->>> 1 -1 - -Test operations involving NaN/Inf ---------------------------------- - ->>> a + float('Inf') -mpfr('inf') ->>> float('Inf') + a -mpfr('inf') ->>> a + float('-Inf') -mpfr('-inf') ->>> float('-Inf') + a -mpfr('-inf') ->>> a + float('nan') -mpfr('nan') ->>> float('nan') + a -mpfr('nan') - ->>> a - float('Inf') -mpfr('-inf') ->>> float('Inf') - a -mpfr('inf') ->>> a - float('-Inf') -mpfr('inf') ->>> float('-Inf') - a -mpfr('-inf') ->>> a - float('nan') -mpfr('nan') ->>> float('nan') - a -mpfr('nan') - ->>> a * float('Inf') -mpfr('inf') ->>> float('Inf') * a -mpfr('inf') ->>> a * float('-Inf') -mpfr('-inf') ->>> float('-Inf') * a -mpfr('-inf') ->>> -a * float('Inf') -mpfr('-inf') ->>> float('Inf') * -a -mpfr('-inf') ->>> -a * float('-Inf') -mpfr('inf') ->>> float('-Inf') * -a -mpfr('inf') ->>> a * float('nan') -mpfr('nan') ->>> float('nan') * a -mpfr('nan') ->>> G.mpz(0) * float('Inf') -mpfr('nan') ->>> G.mpz(0) * float('-Inf') -mpfr('nan') ->>> float('Inf') * G.mpz(0) -mpfr('nan') ->>> float('-Inf') * G.mpz(0) -mpfr('nan') ->>> a / float('Inf') -mpfr('0.0') ->>> -a / float('Inf') -mpfr('-0.0') ->>> float('Inf') / a -mpfr('inf') ->>> float('Inf') / -a -mpfr('-inf') ->>> a / float('-Inf') -mpfr('-0.0') ->>> -a / float('-Inf') -mpfr('0.0') ->>> float('-Inf') / a -mpfr('-inf') ->>> float('-Inf') / -a -mpfr('inf') ->>> a / float('nan') -mpfr('nan') ->>> float('nan') / a -mpfr('nan') ->>> float('nan') / G.mpz(0) -mpfr('nan') ->>> float('nan') / G.mpz(0) -mpfr('nan') - ->>> a - mpfr('Inf') -mpfr('-inf') ->>> mpfr('Inf') - a -mpfr('inf') ->>> a - mpfr('-Inf') -mpfr('inf') ->>> mpfr('-Inf') - a -mpfr('-inf') ->>> a - mpfr('nan') -mpfr('nan') ->>> mpfr('nan') - a -mpfr('nan') ->>> a * mpfr('Inf') -mpfr('inf') ->>> mpfr('Inf') * a -mpfr('inf') ->>> a * mpfr('-Inf') -mpfr('-inf') ->>> mpfr('-Inf') * a -mpfr('-inf') ->>> -a * mpfr('Inf') -mpfr('-inf') ->>> mpfr('Inf') * -a -mpfr('-inf') ->>> -a * mpfr('-Inf') -mpfr('inf') ->>> mpfr('-Inf') * -a -mpfr('inf') ->>> a * mpfr('nan') -mpfr('nan') ->>> mpfr('nan') * a -mpfr('nan') ->>> G.mpz(0) * mpfr('Inf') -mpfr('nan') ->>> G.mpz(0) * mpfr('-Inf') -mpfr('nan') ->>> mpfr('Inf') * G.mpz(0) -mpfr('nan') ->>> mpfr('-Inf') * G.mpz(0) -mpfr('nan') ->>> a / mpfr('Inf') -mpfr('0.0') ->>> -a / mpfr('Inf') -mpfr('-0.0') ->>> mpfr('Inf') / a -mpfr('inf') ->>> mpfr('Inf') / -a -mpfr('-inf') ->>> a / mpfr('-Inf') -mpfr('-0.0') ->>> -a / mpfr('-Inf') -mpfr('0.0') ->>> mpfr('-Inf') / a -mpfr('-inf') ->>> mpfr('-Inf') / -a -mpfr('inf') ->>> a / mpfr('nan') -mpfr('nan') ->>> mpfr('nan') / a -mpfr('nan') ->>> mpfr('nan') / G.mpz(0) -mpfr('nan') ->>> mpfr('nan') / G.mpz(0) -mpfr('nan') - ->>> divmod(a, mpfr('Inf')) -(mpfr('0.0'), mpfr('123.0')) ->>> divmod(a, mpfr('-Inf')) -(mpfr('-1.0'), mpfr('-inf')) ->>> divmod(-a, mpfr('Inf')) -(mpfr('-1.0'), mpfr('inf')) ->>> divmod(-a, mpfr('-Inf')) -(mpfr('0.0'), mpfr('-123.0')) ->>> divmod(a, mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(-a, mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(G.mpz(0), mpfr('Inf')) -(mpfr('0.0'), mpfr('0.0')) ->>> divmod(G.mpz(0), mpfr('-Inf')) -(mpfr('-0.0'), mpfr('-0.0')) ->>> divmod(G.mpz(0), mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) - ->>> divmod(a, mpfr('Inf')) -(mpfr('0.0'), mpfr('123.0')) ->>> divmod(a, mpfr('-Inf')) -(mpfr('-1.0'), mpfr('-inf')) ->>> divmod(-a, mpfr('Inf')) -(mpfr('-1.0'), mpfr('inf')) ->>> divmod(-a, mpfr('-Inf')) -(mpfr('0.0'), mpfr('-123.0')) ->>> divmod(a, mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(-a, mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(G.mpz(0), mpfr('Inf')) -(mpfr('0.0'), mpfr('0.0')) ->>> divmod(G.mpz(0), mpfr('-Inf')) -(mpfr('-0.0'), mpfr('-0.0')) ->>> divmod(G.mpz(0), mpfr('nan')) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), -a) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('Inf'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('-Inf'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) ->>> divmod(mpfr('nan'), G.mpz(0)) -(mpfr('nan'), mpfr('nan')) - -Test bit operations -------------------- - ->>> ~a -mpz(-124) ->>> a&b -mpz(72) ->>> a&int(b) -mpz(72) ->>> int(a)&b -mpz(72) ->>> a|b -mpz(507) ->>> a|int(b) -mpz(507) ->>> int(a)|b -mpz(507) ->>> a^b -mpz(435) ->>> a^int(b) -mpz(435) ->>> int(a)^b -mpz(435) ->>> a<<1 -mpz(246) ->>> int(a)<>> a>>1 -mpz(61) ->>> int(a)>>mpz(1) -mpz(61) ->>> a<<-1 -Traceback (innermost last): - ... -OverflowError: can't convert negative value to unsigned long ->>> a>>-2 -Traceback (innermost last): - ... -OverflowError: can't convert negative value to unsigned long ->>> a<<0 -mpz(123) ->>> a>>0 -mpz(123) ->>> "a" << a -Traceback (most recent call last): - File "", line 1, in -TypeError: cannot convert object to mpz ->>> "a" >> a -Traceback (most recent call last): - File "", line 1, in -TypeError: cannot convert object to mpz ->>> a&mpq(1) -Traceback (most recent call last): - File "", line 1, in -TypeError: cannot convert object to mpz ->>> a|mpq(1) -Traceback (most recent call last): - File "", line 1, in -TypeError: cannot convert object to mpz ->>> a^mpq(1) -Traceback (most recent call last): - File "", line 1, in -TypeError: cannot convert object to mpz - -Test conversions ----------------- - ->>> int(G.mpz(-3)) --3 - -Test Number Protocol --------------------- - ->>> a.numerator -mpz(123) ->>> a.denominator -mpz(1) ->>> a.real -mpz(123) ->>> a.imag -mpz(0) ->>> a.conjugate() -mpz(123) - -Sequence Protocol ------------------ - ->>> a = mpz(10) ->>> a[1] -1 ->>> a[-1] -1 ->>> a[-2] -0 ->>> a[0:2] -mpz(2) ->>> a[0:3] -mpz(2) ->>> a[0:3:-1] -mpz(0) ->>> a[111111111111111111111] -Traceback (most recent call last): - File "", line 1, in -IndexError: argument too large to convert to an index ->>> a["spam"] -Traceback (most recent call last): - File "", line 1, in -TypeError: bit positions must be integers From b7e82d80d665f6f669fd9f837cdffd0ceba151b0 Mon Sep 17 00:00:00 2001 From: Sergey B Kirpichev Date: Mon, 20 Nov 2023 05:58:46 +0300 Subject: [PATCH 6/9] Port test/test_mpfr_trig.txt to pytest framework --- test/runtests.py | 6 +- test/test_functions.py | 283 ++++++++++++++++++++++++- test/test_mpfr_trig.txt | 456 ---------------------------------------- 3 files changed, 273 insertions(+), 472 deletions(-) delete mode 100644 test/test_mpfr_trig.txt diff --git a/test/runtests.py b/test/runtests.py index 85ee1f52..91e9b6ab 100644 --- a/test/runtests.py +++ b/test/runtests.py @@ -24,8 +24,6 @@ print(" Complex library: {0}".format(gmpy2.mpc_version())) print() -mpfr_doctests = ["test_mpfr_trig.txt"] - gmpy2_tests = [os.path.basename(i) for i in glob.glob(os.path.join(test_dir, "test_gmpy2*.txt"))] @@ -33,9 +31,7 @@ failed = 0 attempted = 0 -all_doctests = gmpy2_tests + mpfr_doctests - -for test in sorted(all_doctests): +for test in sorted(gmpy2_tests): result = doctest.testfile(test, globs=globals(), optionflags=doctest.IGNORE_EXCEPTION_DETAIL | doctest.NORMALIZE_WHITESPACE | diff --git a/test/test_functions.py b/test/test_functions.py index d1d30b16..ab2993f6 100644 --- a/test/test_functions.py +++ b/test/test_functions.py @@ -1,17 +1,22 @@ +from fractions import Fraction + import pytest import gmpy2 -from gmpy2 import (can_round, check_range, copy_sign, f2q, fac, fma, fmma, - fmms, fms, from_binary, get_emax_max, get_emin_min, get_exp, - ieee, inf, is_bpsw_prp, is_euler_prp, - is_extra_strong_lucas_prp, is_fermat_prp, is_fibonacci_prp, - is_finite, is_infinite, is_lucas_prp, is_nan, - is_selfridge_prp, is_strong_bpsw_prp, is_strong_lucas_prp, - is_strong_prp, is_strong_selfridge_prp, is_zero, maxnum, - minnum, mpc, mpfr, mpfr_from_old_binary, mpq, - mpq_from_old_binary, mpz, mpz_from_old_binary, nan, norm, - phase, polar, powmod, powmod_sec, proj, rect, root, - root_of_unity, rootn, set_exp, set_sign, sign, zero) +from gmpy2 import (acos, acosh, asin, asinh, atan, atan2, atanh, can_round, + check_range, context, copy_sign, cos, cosh, cot, coth, csc, + csch, degrees, f2q, fac, fma, fmma, fmms, fms, from_binary, + get_context, get_emax_max, get_emin_min, get_exp, ieee, inf, + is_bpsw_prp, is_euler_prp, is_extra_strong_lucas_prp, + is_fermat_prp, is_fibonacci_prp, is_finite, is_infinite, + is_lucas_prp, is_nan, is_selfridge_prp, is_strong_bpsw_prp, + is_strong_lucas_prp, is_strong_prp, is_strong_selfridge_prp, + is_zero, maxnum, minnum, mpc, mpfr, mpfr_from_old_binary, + mpq, mpq_from_old_binary, mpz, mpz_from_old_binary, nan, + norm, phase, polar, powmod, powmod_sec, proj, radians, rect, + root, root_of_unity, rootn, sec, sech, set_context, set_exp, + set_sign, sign, sin, sin_cos, sinh, sinh_cosh, tan, tanh, + zero) def test_root(): @@ -532,3 +537,259 @@ def test_sign(): assert sign(a-b) == -1 assert sign(a) == 1 assert sign(-a) == -1 + + +def test_acos(): + assert acos(mpfr("0.2")).as_integer_ratio() == (mpz(6167402294989009), mpz(4503599627370496)) + + pytest.raises(TypeError, lambda: acos()) + pytest.raises(TypeError, lambda: acos("a")) + pytest.raises(TypeError, lambda: acos(0,0)) + + assert acos(0) == mpfr('1.5707963267948966') + assert acos(mpz(0)) == mpfr('1.5707963267948966') + assert acos(mpq(1,2)) == mpfr('1.0471975511965979') + assert acos(Fraction(1,2)) == mpfr('1.0471975511965979') + assert is_nan(acos(mpfr("nan"))) + assert is_nan(acos(mpfr("inf"))) + assert is_nan(acos(mpfr("-inf"))) + + set_context(context(trap_invalid=True)) + + pytest.raises(gmpy2.InvalidOperationError, lambda: acos(mpfr("nan"))) + pytest.raises(gmpy2.InvalidOperationError, lambda: acos(mpfr("inf"))) + pytest.raises(gmpy2.InvalidOperationError, lambda: acos(mpfr("-inf"))) + + set_context(context(precision=100)) + + assert acos(mpfr("0.2")) == mpfr('1.3694384060045658277761961394221',100) + assert get_context().precision == 100 + assert get_context().inexact + + +def test_asin(): + assert gmpy2.asin(mpfr("0.2")).as_integer_ratio() == (mpz(7254683656315453), mpz(36028797018963968)) + + pytest.raises(TypeError, lambda: asin()) + pytest.raises(TypeError, lambda: asin("a")) + pytest.raises(TypeError, lambda: asin(0,0)) + + assert asin(0) == mpfr('0.0') + assert asin(mpz(0)) == mpfr('0.0') + assert asin(mpq(1,2)) == mpfr('0.52359877559829893') + assert asin(Fraction(1,2)) == mpfr('0.52359877559829893') + assert is_nan(asin(mpfr("nan"))) + assert is_nan(asin(mpfr("inf"))) + assert is_nan(asin(mpfr("-inf"))) + + set_context(context(trap_invalid=True)) + + pytest.raises(gmpy2.InvalidOperationError, lambda: asin(mpfr("nan"))) + pytest.raises(gmpy2.InvalidOperationError, lambda: asin(mpfr("inf"))) + pytest.raises(gmpy2.InvalidOperationError, lambda: asin(mpfr("-inf"))) + + set_context(context(precision=100)) + + assert asin(mpfr("0.2")) == mpfr('0.20135792079033079145512555221757',100) + + assert get_context().precision == 100 + assert get_context().inexact + + +def test_atan(): + assert atan(mpfr("0.2")).as_integer_ratio() == (mpz(1777981139569027), mpz(9007199254740992)) + assert atan(mpfr("100")).as_integer_ratio() == (mpz(3514601628432273), mpz(2251799813685248)) + + pytest.raises(TypeError, lambda: atan()) + pytest.raises(TypeError, lambda: atan("a")) + pytest.raises(TypeError, lambda: atan(0,0)) + + assert atan(0) == mpfr('0.0') + assert atan(mpz(0)) == mpfr('0.0') + assert atan(mpq(1,2)) == mpfr('0.46364760900080609') + assert atan(Fraction(1,2)) == mpfr('0.46364760900080609') + assert is_nan(gmpy2.atan(mpfr("nan"))) + assert atan(mpfr("inf")) == mpfr('1.5707963267948966') + assert atan(mpfr("-inf")) == mpfr('-1.5707963267948966') + + set_context(context(trap_invalid=True)) + + pytest.raises(gmpy2.InvalidOperationError, lambda: atan(mpfr("nan"))) + + set_context(context(precision=100)) + + assert gmpy2.atan(mpfr("0.2")) == mpfr('0.19739555984988075837004976519484',100) + assert get_context().precision == 100 + assert get_context().inexact + + +def test_atan2(): + assert atan2(1,2).as_integer_ratio() == (mpz(8352332796509007), mpz(18014398509481984)) + assert atan2(-1,2).as_integer_ratio() == (mpz(-8352332796509007), mpz(18014398509481984)) + assert atan2(1,-2).as_integer_ratio() == (mpz(3015098076232407), mpz(1125899906842624)) + assert atan2(-1,-2).as_integer_ratio() == (mpz(-3015098076232407), mpz(1125899906842624)) + assert atan2(float("0"),float("0")).as_integer_ratio() == (mpz(0), mpz(1)) + assert atan2(float("-0"),float("0")).as_integer_ratio() == (mpz(0), mpz(1)) + assert atan2(float("0"),float("-0")).as_integer_ratio() == (mpz(884279719003555), mpz(281474976710656)) + assert atan2(float("-0"),float("-0")).as_integer_ratio() == (mpz(-884279719003555), mpz(281474976710656)) + assert atan2(float("inf"),float("inf")).as_integer_ratio() == (mpz(884279719003555), mpz(1125899906842624)) + assert atan2(float("-inf"),float("inf")).as_integer_ratio() == (mpz(-884279719003555), mpz(1125899906842624)) + assert atan2(float("inf"),float("-inf")).as_integer_ratio() == (mpz(2652839157010665), mpz(1125899906842624)) + assert atan2(float("-inf"),float("-inf")).as_integer_ratio() == (mpz(-2652839157010665), mpz(1125899906842624)) + + +def test_cos(): + assert cos(mpfr("0.2")).as_integer_ratio() == (mpz(4413827474764093), mpz(4503599627370496)) + assert cos(mpfr("20")).as_integer_ratio() == (mpz(7351352886077503), mpz(18014398509481984)) or (sys.platform == 'win32') + assert cos(mpfr("2000")).as_integer_ratio() == (mpz(-3309781376808469), mpz(9007199254740992)) + + pytest.raises(TypeError, lambda: cos()) + pytest.raises(TypeError, lambda: cos("a")) + pytest.raises(TypeError, lambda: cos(0,0)) + + assert cos(0) == mpfr('1.0') + assert cos(mpz(0)) == mpfr('1.0') + assert cos(mpq(1,2)) == mpfr('0.87758256189037276') + assert cos(Fraction(1,2)) == mpfr('0.87758256189037276') + assert is_nan(cos(mpfr("nan"))) + assert is_nan(cos(mpfr("inf"))) + assert is_nan(cos(mpfr("-inf"))) + + set_context(context(trap_invalid=True)) + + pytest.raises(gmpy2.InvalidOperationError, lambda: cos(mpfr("nan"))) + pytest.raises(gmpy2.InvalidOperationError, lambda: cos(mpfr("inf"))) + pytest.raises(gmpy2.InvalidOperationError, lambda: cos(mpfr("-inf"))) + + set_context(context(precision=100)) + + assert cos(mpfr("0.2")) == mpfr('0.98006657784124163112419651674809',100) + assert get_context().precision == 100 + assert get_context().inexact + + +def test_cot(): + assert cot(mpfr("0.2")).as_integer_ratio() == (mpz(173569956714485), mpz(35184372088832)) + assert cot(gmpy2.const_pi()).as_integer_ratio() == (mpz(-8165619676597685), mpz(1)) + assert cot(1) == mpfr('0.64209261593433076') + assert cot(float('0')) == mpfr('inf') + assert cot(float('-0')) == mpfr('-inf') + assert cot(mpfr('0')) == mpfr('inf') + assert cot(mpfr('-0')) == mpfr('-inf') + + +def test_csc(): + r2 = mpfr('5.6') + + assert csc(r2) == mpfr('-1.5841166632383596') + + +def test_sec(): + r2 = mpfr('5.6') + + assert sec(r2) == mpfr('1.2893811186238056') + + +def test_sin(): + r = mpfr(5.6) + + assert sin(r) == mpfr('-0.63126663787232162') + assert sin(r) == sin(5.6) + + +def test_sin_cos(): + r = mpfr(5.6) + + assert sin_cos(r) == (mpfr('-0.63126663787232162'), mpfr('0.77556587851024961')) + assert sin_cos(r) == sin_cos(5.6) + assert sin_cos(r) == (sin(r), cos(r)) + + +def test_tan(): + r = mpfr(5.6) + + assert tan(r) == mpfr('-0.8139432836897027') + + +def test_acosh(): + r = mpfr(5.6) + + assert acosh(r) == mpfr('2.4078447868719399') + +def test_asinh(): + r = mpfr(5.6) + + assert asinh(r) == mpfr('2.4237920435875173') + + +def test_atanh(): + assert atanh(mpfr(0.365)) == mpfr('0.38264235436318422') + assert atanh(mpfr(0.365)) == atanh(0.365) + + +def test_cosh(): + r = mpfr(5.6) + + assert cosh(r) == mpfr('135.2150526449345') + assert cosh(r) == cosh(5.6) + + +def test_coth(): + r = mpfr(5.6) + + assert coth(r) == mpfr('1.0000273487661038') + + +def test_csch(): + r = mpfr(5.6) + + assert csch(r) == mpfr('0.0073958285649757295') + + +def test_degrees(): + rad = mpfr(1.57) + ctx = get_context() + + assert ctx.degrees(rad) == mpfr('89.954373835539243') + assert degrees(rad) == mpfr('89.954373835539243') + assert degrees(1) == mpfr('57.295779513082323') + + +def test_radians(): + deg = mpfr(90) + ctx = get_context() + + assert ctx.radians(deg) == mpfr('1.5707963267948966') + assert radians(deg) == mpfr('1.5707963267948966') + assert radians(45) == mpfr('0.78539816339744828') + assert radians(mpz(20)) == mpfr('0.3490658503988659') + assert radians(mpfr('inf')) == mpfr('inf') + assert is_nan(radians(mpfr('nan'))) + + +def test_sech(): + r = mpfr(5.6) + + assert sech(r) == mpfr('0.0073956263037217584') + + +def test_sinh(): + r = mpfr(5.6) + + + assert sinh(r) == mpfr('135.21135478121803') + assert sinh(r) == gmpy2.sinh(5.6) + + +def test_sinh_cosh(): + r = mpfr(5.6) + + assert sinh_cosh(r) == (mpfr('135.21135478121803'), mpfr('135.2150526449345')) + assert sinh_cosh(r) == sinh_cosh(5.6) + assert sinh_cosh(r) == (sinh(r), cosh(r)) + + +def test_tanh(): + r = mpfr(5.6) + + assert tanh(r) == mpfr('0.99997265198183083') diff --git a/test/test_mpfr_trig.txt b/test/test_mpfr_trig.txt deleted file mode 100644 index d0b10b9b..00000000 --- a/test/test_mpfr_trig.txt +++ /dev/null @@ -1,456 +0,0 @@ -MPFR Functionality -================== - ->>> import gmpy2 ->>> from gmpy2 import mpfr, mpq, mpz ->>> from fractions import Fraction as F ->>> import sys - -Test trigonometric operations -============================= - -Note: gmpy2 returns InvalidOperationError whereas the math module returns -ValueError. The test of acos verifies that InvalidOperationError is sub- -classed from ValueError. - -Note: The math module assumes non-signaling NaNs; math.acos(float("nan")) -does not raise an exception. But math.acos(float("inf")) and -math.acos(float("-inf")) do raise exceptions. MPFR treats NaN as a -signaling NaN and raises an exception if trap_invalid is True. - -Test acos ---------- - ->>> gmpy2.set_context(gmpy2.context()) ->>> gmpy2.acos(mpfr("0.2")).as_integer_ratio() -(mpz(6167402294989009), mpz(4503599627370496)) ->>> gmpy2.acos() -Traceback (most recent call last): - File "", line 1, in -TypeError: acos() takes exactly one argument (0 given) ->>> gmpy2.acos("a") -Traceback (most recent call last): - File "", line 1, in -TypeError: acos() argument type not supported ->>> gmpy2.acos(0,0) -Traceback (most recent call last): - File "", line 1, in -TypeError: acos() takes exactly one argument (2 given) ->>> gmpy2.acos(0) -mpfr('1.5707963267948966') ->>> gmpy2.acos(mpz(0)) -mpfr('1.5707963267948966') ->>> gmpy2.acos(mpq(1,2)) -mpfr('1.0471975511965979') ->>> gmpy2.acos(F(1,2)) -mpfr('1.0471975511965979') ->>> gmpy2.acos(mpfr("nan")) -mpfr('nan') ->>> gmpy2.acos(mpfr("inf")) -mpfr('nan') ->>> gmpy2.acos(mpfr("-inf")) -mpfr('nan') ->>> gmpy2.set_context(gmpy2.context(trap_invalid=True)) ->>> gmpy2.acos(mpfr("nan")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.acos(mpfr("inf")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.acos(mpfr("-inf")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.set_context(gmpy2.context(precision=100)) ->>> gmpy2.acos(mpfr("0.2")) -mpfr('1.3694384060045658277761961394221',100) ->>> gmpy2.get_context() -context(precision=100, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=True, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) - -Test asin ---------- - ->>> gmpy2.set_context(gmpy2.context()) ->>> gmpy2.asin(mpfr("0.2")).as_integer_ratio() -(mpz(7254683656315453), mpz(36028797018963968)) ->>> gmpy2.asin() -Traceback (most recent call last): - File "", line 1, in -TypeError: asin() takes exactly one argument (0 given) ->>> gmpy2.asin("a") -Traceback (most recent call last): - File "", line 1, in -TypeError: asin() argument type not supported ->>> gmpy2.asin(0,0) -Traceback (most recent call last): - File "", line 1, in -TypeError: asin() takes exactly one argument (2 given) ->>> gmpy2.asin(0) -mpfr('0.0') ->>> gmpy2.asin(mpz(0)) -mpfr('0.0') ->>> gmpy2.asin(mpq(1,2)) -mpfr('0.52359877559829893') ->>> gmpy2.asin(F(1,2)) -mpfr('0.52359877559829893') ->>> gmpy2.asin(mpfr("nan")) -mpfr('nan') ->>> gmpy2.asin(mpfr("inf")) -mpfr('nan') ->>> gmpy2.asin(mpfr("-inf")) -mpfr('nan') ->>> gmpy2.set_context(gmpy2.context(trap_invalid=True)) ->>> gmpy2.asin(mpfr("nan")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.asin(mpfr("inf")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.asin(mpfr("-inf")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.set_context(gmpy2.context(precision=100)) ->>> gmpy2.asin(mpfr("0.2")) -mpfr('0.20135792079033079145512555221757',100) ->>> gmpy2.get_context() -context(precision=100, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=True, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) - -Test atan ---------- - ->>> gmpy2.set_context(gmpy2.context()) ->>> gmpy2.atan(mpfr("0.2")).as_integer_ratio() -(mpz(1777981139569027), mpz(9007199254740992)) ->>> gmpy2.atan(mpfr("100")).as_integer_ratio() -(mpz(3514601628432273), mpz(2251799813685248)) ->>> gmpy2.atan() -Traceback (most recent call last): - File "", line 1, in -TypeError: atan() takes exactly one argument (0 given) ->>> gmpy2.atan("a") -Traceback (most recent call last): - File "", line 1, in -TypeError: atan() argument type not supported ->>> gmpy2.atan(0,0) -Traceback (most recent call last): - File "", line 1, in -TypeError: atan() takes exactly one argument (2 given) ->>> gmpy2.atan(0) -mpfr('0.0') ->>> gmpy2.atan(mpz(0)) -mpfr('0.0') ->>> gmpy2.atan(mpq(1,2)) -mpfr('0.46364760900080609') ->>> gmpy2.atan(F(1,2)) -mpfr('0.46364760900080609') ->>> gmpy2.atan(mpfr("nan")) -mpfr('nan') ->>> gmpy2.atan(mpfr("inf")) -mpfr('1.5707963267948966') ->>> gmpy2.atan(mpfr("-inf")) -mpfr('-1.5707963267948966') ->>> gmpy2.set_context(gmpy2.context(trap_invalid=True)) ->>> gmpy2.atan(mpfr("nan")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.set_context(gmpy2.context(precision=100)) ->>> gmpy2.atan(mpfr("0.2")) -mpfr('0.19739555984988075837004976519484',100) ->>> gmpy2.get_context() -context(precision=100, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=True, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) - -Test atan2 ----------- - ->>> gmpy2.set_context(gmpy2.context()) ->>> gmpy2.atan2(1,2).as_integer_ratio() -(mpz(8352332796509007), mpz(18014398509481984)) ->>> gmpy2.atan2(-1,2).as_integer_ratio() -(mpz(-8352332796509007), mpz(18014398509481984)) ->>> gmpy2.atan2(1,-2).as_integer_ratio() -(mpz(3015098076232407), mpz(1125899906842624)) ->>> gmpy2.atan2(-1,-2).as_integer_ratio() -(mpz(-3015098076232407), mpz(1125899906842624)) ->>> gmpy2.atan2(float("0"),float("0")).as_integer_ratio() -(mpz(0), mpz(1)) ->>> gmpy2.atan2(float("-0"),float("0")).as_integer_ratio() -(mpz(0), mpz(1)) ->>> gmpy2.atan2(float("0"),float("-0")).as_integer_ratio() -(mpz(884279719003555), mpz(281474976710656)) ->>> gmpy2.atan2(float("-0"),float("-0")).as_integer_ratio() -(mpz(-884279719003555), mpz(281474976710656)) ->>> gmpy2.atan2(float("inf"),float("inf")).as_integer_ratio() -(mpz(884279719003555), mpz(1125899906842624)) ->>> gmpy2.atan2(float("-inf"),float("inf")).as_integer_ratio() -(mpz(-884279719003555), mpz(1125899906842624)) ->>> gmpy2.atan2(float("inf"),float("-inf")).as_integer_ratio() -(mpz(2652839157010665), mpz(1125899906842624)) ->>> gmpy2.atan2(float("-inf"),float("-inf")).as_integer_ratio() -(mpz(-2652839157010665), mpz(1125899906842624)) - -Test cos --------- - ->>> gmpy2.set_context(gmpy2.context()) ->>> gmpy2.cos(mpfr("0.2")).as_integer_ratio() -(mpz(4413827474764093), mpz(4503599627370496)) ->>> gmpy2.cos(mpfr("20")).as_integer_ratio() == (mpz(7351352886077503), mpz(18014398509481984)) or (sys.platform == 'win32') -True ->>> gmpy2.cos(mpfr("2000")).as_integer_ratio() -(mpz(-3309781376808469), mpz(9007199254740992)) ->>> gmpy2.cos() -Traceback (most recent call last): - File "", line 1, in -TypeError: cos() takes exactly one argument (0 given) ->>> gmpy2.cos("a") -Traceback (most recent call last): - File "", line 1, in -TypeError: cos() argument type not supported ->>> gmpy2.cos(0,0) -Traceback (most recent call last): - File "", line 1, in -TypeError: cos() takes exactly one argument (2 given) ->>> gmpy2.cos(0) -mpfr('1.0') ->>> gmpy2.cos(mpz(0)) -mpfr('1.0') ->>> gmpy2.cos(mpq(1,2)) -mpfr('0.87758256189037276') ->>> gmpy2.cos(F(1,2)) -mpfr('0.87758256189037276') ->>> gmpy2.cos(mpfr("nan")) -mpfr('nan') ->>> gmpy2.cos(mpfr("inf")) -mpfr('nan') ->>> gmpy2.cos(mpfr("-inf")) -mpfr('nan') ->>> gmpy2.set_context(gmpy2.context(trap_invalid=True)) ->>> gmpy2.cos(mpfr("nan")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.cos(mpfr("inf")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.cos(mpfr("-inf")) -Traceback (most recent call last): - File "", line 1, in -InvalidOperationError: invalid operation ->>> gmpy2.set_context(gmpy2.context(precision=100)) ->>> gmpy2.cos(mpfr("0.2")) -mpfr('0.98006657784124163112419651674809',100) ->>> gmpy2.get_context() -context(precision=100, real_prec=Default, imag_prec=Default, - round=RoundToNearest, real_round=Default, imag_round=Default, - emax=1073741823, emin=-1073741823, - subnormalize=False, - trap_underflow=False, underflow=False, - trap_overflow=False, overflow=False, - trap_inexact=False, inexact=True, - trap_invalid=False, invalid=False, - trap_erange=False, erange=False, - trap_divzero=False, divzero=False, - allow_complex=False, - rational_division=False, - allow_release_gil=False) - -Test cot --------- - ->>> gmpy2.set_context(gmpy2.context()) ->>> gmpy2.cot(mpfr("0.2")).as_integer_ratio() -(mpz(173569956714485), mpz(35184372088832)) ->>> gmpy2.cot(gmpy2.const_pi()).as_integer_ratio() -(mpz(-8165619676597685), mpz(1)) ->>> gmpy2.cot(1) -mpfr('0.64209261593433076') ->>> gmpy2.cot(float('0')) -mpfr('inf') ->>> gmpy2.cot(float('-0')) -mpfr('-inf') ->>> gmpy2.cot(mpfr('0')) -mpfr('inf') ->>> gmpy2.cot(mpfr('-0')) -mpfr('-inf') - -Test csc --------- - ->>> r2 = mpfr('5.6') ->>> gmpy2.csc(r2) -mpfr('-1.5841166632383596') - -Test sec --------- - ->>> gmpy2.sec(r2) -mpfr('1.2893811186238056') - -Test sin --------- - ->>> r = mpfr(5.6) ->>> gmpy2.sin(r) -mpfr('-0.63126663787232162') ->>> gmpy2.sin(r) == gmpy2.sin(5.6) -True - -Test sin_cos ------------- - ->>> gmpy2.sin_cos(r) -(mpfr('-0.63126663787232162'), mpfr('0.77556587851024961')) ->>> gmpy2.sin_cos(r) == gmpy2.sin_cos(5.6) -True ->>> gmpy2.sin_cos(r) == (gmpy2.sin(r), gmpy2.cos(r)) -True - -Test tan --------- - ->>> gmpy2.tan(r) -mpfr('-0.8139432836897027') - -Test acosh ----------- - ->>> gmpy2.acosh(r) -mpfr('2.4078447868719399') - -Test asinh ----------- - ->>> gmpy2.asinh(r) -mpfr('2.4237920435875173') - -Test atanh ----------- - ->>> gmpy2.atanh(mpfr(0.365)) -mpfr('0.38264235436318422') ->>> gmpy2.atanh(mpfr(0.365)) == gmpy2.atanh(0.365) -True - -Test cosh ---------- - ->>> gmpy2.cosh(r) -mpfr('135.2150526449345') ->>> gmpy2.cosh(r) == gmpy2.cosh(5.6) -True - -Test coth ---------- - ->>> gmpy2.coth(r) -mpfr('1.0000273487661038') - -Test csch ---------- - ->>> gmpy2.csch(r) -mpfr('0.0073958285649757295') - ->>> gmpy2.csch(r) -mpfr('0.0073958285649757295') - -Test degrees ------------- ->>> rad = mpfr(1.57) ->>> ctx = gmpy2.get_context() ->>> ctx.degrees(rad) -mpfr('89.954373835539243') ->>> gmpy2.degrees(rad) -mpfr('89.954373835539243') ->>> gmpy2.degrees(1) -mpfr('57.295779513082323') - -Test radians -------------- - ->>> deg = mpfr(90) ->>> ctx.radians(deg) -mpfr('1.5707963267948966') ->>> gmpy2.radians(deg) -mpfr('1.5707963267948966') ->>> gmpy2.radians(45) -mpfr('0.78539816339744828') ->>> gmpy2.radians(mpz(20)) -mpfr('0.3490658503988659') ->>> gmpy2.radians(mpfr('inf')) -mpfr('inf') ->>> gmpy2.radians(mpfr('nan')) -mpfr('nan') - -Test sech ---------- - ->>> gmpy2.sech(r) -mpfr('0.0073956263037217584') - -Test sinh ---------- - ->>> gmpy2.sinh(r) -mpfr('135.21135478121803') ->>> gmpy2.sinh(r) == gmpy2.sinh(5.6) -True - -Test sinh_cosh --------------- - ->>> gmpy2.sinh_cosh(r) -(mpfr('135.21135478121803'), mpfr('135.2150526449345')) ->>> gmpy2.sinh_cosh(r) == gmpy2.sinh_cosh(5.6) -True ->>> gmpy2.sinh_cosh(r) == (gmpy2.sinh(r), gmpy2.cosh(r)) -True - -Test tanh ---------- - ->>> gmpy2.tanh(r) -mpfr('0.99997265198183083') From fafa9191e94d67586c4274bda952d83cf79e7456 Mon Sep 17 00:00:00 2001 From: Sergey B Kirpichev Date: Tue, 21 Nov 2023 06:26:26 +0300 Subject: [PATCH 7/9] Port test/test_gmpy2_mpz_divmod.txt to pytest framework --- test/test_functions.py | 138 ++++++++++++++++++++- test/test_gmpy2_mpz_divmod.txt | 215 --------------------------------- 2 files changed, 132 insertions(+), 221 deletions(-) delete mode 100644 test/test_gmpy2_mpz_divmod.txt diff --git a/test/test_functions.py b/test/test_functions.py index ab2993f6..0ecee7c0 100644 --- a/test/test_functions.py +++ b/test/test_functions.py @@ -3,9 +3,10 @@ import pytest import gmpy2 -from gmpy2 import (acos, acosh, asin, asinh, atan, atan2, atanh, can_round, - check_range, context, copy_sign, cos, cosh, cot, coth, csc, - csch, degrees, f2q, fac, fma, fmma, fmms, fms, from_binary, +from gmpy2 import (acos, acosh, asin, asinh, atan, atan2, atanh, c_div, + c_divmod, c_mod, can_round, check_range, context, copy_sign, + cos, cosh, cot, coth, csc, csch, degrees, f2q, f_div, + f_divmod, f_mod, fac, fma, fmma, fmms, fms, from_binary, get_context, get_emax_max, get_emin_min, get_exp, ieee, inf, is_bpsw_prp, is_euler_prp, is_extra_strong_lucas_prp, is_fermat_prp, is_fibonacci_prp, is_finite, is_infinite, @@ -15,8 +16,8 @@ mpq, mpq_from_old_binary, mpz, mpz_from_old_binary, nan, norm, phase, polar, powmod, powmod_sec, proj, radians, rect, root, root_of_unity, rootn, sec, sech, set_context, set_exp, - set_sign, sign, sin, sin_cos, sinh, sinh_cosh, tan, tanh, - zero) + set_sign, sign, sin, sin_cos, sinh, sinh_cosh, t_div, + t_divmod, t_mod, tan, tanh, zero) def test_root(): @@ -776,7 +777,6 @@ def test_sech(): def test_sinh(): r = mpfr(5.6) - assert sinh(r) == mpfr('135.21135478121803') assert sinh(r) == gmpy2.sinh(5.6) @@ -793,3 +793,129 @@ def test_tanh(): r = mpfr(5.6) assert tanh(r) == mpfr('0.99997265198183083') + + +def test_c_divmod(): + a = mpz(123) + b = mpz(456) + + pytest.raises(TypeError, lambda: c_divmod(1)) + pytest.raises(TypeError, lambda: c_divmod(1, 'a')) + pytest.raises(ZeroDivisionError, lambda: c_divmod(a,0)) + + assert c_divmod(b,a) == (mpz(4), mpz(-36)) + assert c_divmod(b,-a) == (mpz(-3), mpz(87)) + assert c_divmod(-b,a) == (mpz(-3), mpz(-87)) + assert c_divmod(-b,-a) == (mpz(4), mpz(36)) + + +def test_c_div(): + a = mpz(123) + b = mpz(456) + + pytest.raises(TypeError, lambda: c_div(1)) + pytest.raises(TypeError, lambda: c_div(1, 'a')) + pytest.raises(ZeroDivisionError, lambda: c_div(a,0)) + + assert c_div(b,a) == mpz(4) + assert c_div(b,-a) == mpz(-3) + assert c_div(-b,a) == mpz(-3) + assert c_div(-b,-a) == mpz(4) + + +def test_c_mod(): + a = mpz(123) + b = mpz(456) + + pytest.raises(TypeError, lambda: c_mod(1)) + pytest.raises(TypeError, lambda: c_mod(1, 'a')) + pytest.raises(ZeroDivisionError, lambda: c_mod(a,0)) + + assert c_mod(b,a) == mpz(-36) + assert c_mod(b,-a) == mpz(87) + assert c_mod(-b,a) == mpz(-87) + assert c_mod(-b,-a) == mpz(36) + + +def test_f_divmod(): + a = mpz(123) + b = mpz(456) + + pytest.raises(TypeError, lambda: f_divmod(1)) + pytest.raises(TypeError, lambda: f_divmod(1, 'a')) + pytest.raises(ZeroDivisionError, lambda: f_divmod(a,0)) + + assert f_divmod(b,a) == (mpz(3), mpz(87)) + assert f_divmod(b,-a) == (mpz(-4), mpz(-36)) + assert f_divmod(-b,a) == (mpz(-4), mpz(36)) + assert f_divmod(-b,-a) == (mpz(3), mpz(-87)) + + +def test_f_div(): + a = mpz(123) + b = mpz(456) + + pytest.raises(TypeError, lambda: f_div(1)) + pytest.raises(TypeError, lambda: f_div(1, 'a')) + pytest.raises(ZeroDivisionError, lambda: f_div(a,0)) + + assert f_div(b,a) == mpz(3) + assert f_div(b,-a) == mpz(-4) + assert f_div(-b,a) == mpz(-4) + assert f_div(-b,-a) == mpz(3) + + +def test_f_mod(): + a = mpz(123) + b = mpz(456) + + pytest.raises(TypeError, lambda: f_mod(1)) + pytest.raises(TypeError, lambda: f_mod(1, 'a')) + pytest.raises(ZeroDivisionError, lambda: f_mod(a,0)) + + assert f_mod(b,a) == mpz(87) + assert f_mod(b,-a) == mpz(-36) + assert f_mod(-b,a) == mpz(36) + assert f_mod(-b,-a) == mpz(-87) + + +def test_t_divmod(): + a = mpz(123) + b = mpz(456) + + pytest.raises(TypeError, lambda: t_divmod(1)) + pytest.raises(TypeError, lambda: t_divmod(1, 'a')) + pytest.raises(ZeroDivisionError, lambda: t_divmod(a,0)) + + assert t_divmod(b,a) == (mpz(3), mpz(87)) + assert t_divmod(b,-a) == (mpz(-3), mpz(87)) + assert t_divmod(-b,a) == (mpz(-3), mpz(-87)) + assert t_divmod(-b,-a) == (mpz(3), mpz(-87)) + + +def test_t_div(): + a = mpz(123) + b = mpz(456) + + pytest.raises(TypeError, lambda: t_div(1)) + pytest.raises(TypeError, lambda: t_div(1, 'a')) + pytest.raises(ZeroDivisionError, lambda: t_div(a,0)) + + assert t_div(b,a) == mpz(3) + assert t_div(b,-a) == mpz(-3) + assert t_div(-b,a) == mpz(-3) + assert t_div(-b,-a) == mpz(3) + + +def test_t_mod(): + a = mpz(123) + b = mpz(456) + + pytest.raises(TypeError, lambda: t_mod(1)) + pytest.raises(TypeError, lambda: t_mod(1, 'a')) + pytest.raises(ZeroDivisionError, lambda: t_mod(a,0)) + + assert t_mod(b,a) == mpz(87) + assert t_mod(b,-a) == mpz(87) + assert t_mod(-b,a) == mpz(-87) + assert t_mod(-b,-a) == mpz(-87) diff --git a/test/test_gmpy2_mpz_divmod.txt b/test/test_gmpy2_mpz_divmod.txt deleted file mode 100644 index 42fe63b8..00000000 --- a/test/test_gmpy2_mpz_divmod.txt +++ /dev/null @@ -1,215 +0,0 @@ -Test gmpy2_mpz_divmod.c -===================== - ->>> import gmpy2 ->>> from gmpy2 import mpz ->>> a = mpz(123) ->>> b = mpz(456) - -Test c_divmod -------------- ->>> gmpy2.c_divmod(1) -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.c_divmod(1, 'a') -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.c_divmod(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: ->>> gmpy2.c_divmod(b,a) -(mpz(4), mpz(-36)) ->>> gmpy2.c_divmod(b,-a) -(mpz(-3), mpz(87)) ->>> gmpy2.c_divmod(-b,a) -(mpz(-3), mpz(-87)) ->>> gmpy2.c_divmod(-b,-a) -(mpz(4), mpz(36)) - -Test c_div ----------- ->>> gmpy2.c_div(1) -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.c_div(1, 'a') -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.c_div(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: ->>> gmpy2.c_div(b,a) -mpz(4) ->>> gmpy2.c_div(b,-a) -mpz(-3) ->>> gmpy2.c_div(-b,a) -mpz(-3) ->>> gmpy2.c_div(-b,-a) -mpz(4) - -Test c_mod ----------- ->>> gmpy2.c_mod(1) -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.c_mod(1, 'a') -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.c_mod(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: ->>> gmpy2.c_mod(b,a) -mpz(-36) ->>> gmpy2.c_mod(b,-a) -mpz(87) ->>> gmpy2.c_mod(-b,a) -mpz(-87) ->>> gmpy2.c_mod(-b,-a) -mpz(36) - -Test f_divmod -------------- ->>> gmpy2.f_divmod(1) -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.f_divmod(1, 'a') -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.f_divmod(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: ->>> gmpy2.f_divmod(b,a) -(mpz(3), mpz(87)) ->>> gmpy2.f_divmod(b,-a) -(mpz(-4), mpz(-36)) ->>> gmpy2.f_divmod(-b,a) -(mpz(-4), mpz(36)) ->>> gmpy2.f_divmod(-b,-a) -(mpz(3), mpz(-87)) - -Test f_div ----------- ->>> gmpy2.f_div(1) -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.f_div(1, 'a') -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.f_div(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: ->>> gmpy2.f_div(b,a) -mpz(3) ->>> gmpy2.f_div(b,-a) -mpz(-4) ->>> gmpy2.f_div(-b,a) -mpz(-4) ->>> gmpy2.f_div(-b,-a) -mpz(3) - -Test f_mod ----------- ->>> gmpy2.f_mod(1) -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.f_mod(1, 'a') -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.f_mod(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: ->>> gmpy2.f_mod(b,a) -mpz(87) ->>> gmpy2.f_mod(b,-a) -mpz(-36) ->>> gmpy2.f_mod(-b,a) -mpz(36) ->>> gmpy2.f_mod(-b,-a) -mpz(-87) - -Test t_divmod -------------- ->>> gmpy2.t_divmod(1) -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.t_divmod(1, 'a') -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.t_divmod(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: ->>> gmpy2.t_divmod(b,a) -(mpz(3), mpz(87)) ->>> gmpy2.t_divmod(b,-a) -(mpz(-3), mpz(87)) ->>> gmpy2.t_divmod(-b,a) -(mpz(-3), mpz(-87)) ->>> gmpy2.t_divmod(-b,-a) -(mpz(3), mpz(-87)) - -Test t_div ----------- ->>> gmpy2.t_div(1) -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.t_div(1, 'a') -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.t_div(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: ->>> gmpy2.t_div(b,a) -mpz(3) ->>> gmpy2.t_div(b,-a) -mpz(-3) ->>> gmpy2.t_div(-b,a) -mpz(-3) ->>> gmpy2.t_div(-b,-a) -mpz(3) - -Test t_mod ----------- ->>> gmpy2.t_mod(1) -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.t_mod(1, 'a') -Traceback (most recent call last): - ... -TypeError: ->>> gmpy2.t_mod(a,0) -Traceback (most recent call last): - ... -ZeroDivisionError: ->>> gmpy2.t_mod(b,a) -mpz(87) ->>> gmpy2.t_mod(b,-a) -mpz(87) ->>> gmpy2.t_mod(-b,a) -mpz(-87) ->>> gmpy2.t_mod(-b,-a) -mpz(-87) - From 654ee22021b9c82870769ccba407326896ab171a Mon Sep 17 00:00:00 2001 From: Sergey B Kirpichev Date: Tue, 21 Nov 2023 08:29:46 +0300 Subject: [PATCH 8/9] Improve coverage --- test/test_context.py | 64 ++++++++++++++++++++++++++++++++++++++++++ test/test_functions.py | 61 ++++++++++++++++++++++------------------ test/test_mpq.py | 24 ++++++++++------ 3 files changed, 113 insertions(+), 36 deletions(-) diff --git a/test/test_context.py b/test/test_context.py index d8dd1356..dfe77623 100644 --- a/test/test_context.py +++ b/test/test_context.py @@ -154,3 +154,67 @@ def test_local_context(): assert (ctx.precision == 53 and ctx.emax == 1073741823 and ctx.emin == -1073741823 and not ctx.subnormalize) + + +def test_context_repr(): + ctx = get_context() + assert repr(ctx) == \ +"""context(precision=53, real_prec=Default, imag_prec=Default,\n\ + round=RoundToNearest, real_round=Default, imag_round=Default,\n\ + emax=1073741823, emin=-1073741823,\n subnormalize=False,\n\ + trap_underflow=False, underflow=False,\n trap_overflow=False,\ + overflow=False,\n trap_inexact=False, inexact=False,\n\ + trap_invalid=False, invalid=False,\n trap_erange=False,\ + erange=False,\n trap_divzero=False, divzero=False,\n\ + allow_complex=False,\n rational_division=False,\n\ + allow_release_gil=False)""" + + ctx.real_prec = 100 + ctx.imag_prec = 200 + assert repr(ctx) == \ +"""context(precision=53, real_prec=100, imag_prec=200,\n\ + round=RoundToNearest, real_round=Default, imag_round=Default,\n\ + emax=1073741823, emin=-1073741823,\n subnormalize=False,\n\ + trap_underflow=False, underflow=False,\n trap_overflow=False,\ + overflow=False,\n trap_inexact=False, inexact=False,\n\ + trap_invalid=False, invalid=False,\n trap_erange=False,\ + erange=False,\n trap_divzero=False, divzero=False,\n\ + allow_complex=False,\n rational_division=False,\n\ + allow_release_gil=False)""" + ctx.trap_invalid = True + assert repr(ctx) == \ +"""context(precision=53, real_prec=100, imag_prec=200,\n\ + round=RoundToNearest, real_round=Default, imag_round=Default,\n\ + emax=1073741823, emin=-1073741823,\n subnormalize=False,\n\ + trap_underflow=False, underflow=False,\n trap_overflow=False,\ + overflow=False,\n trap_inexact=False, inexact=False,\n\ + trap_invalid=True, invalid=False,\n trap_erange=False,\ + erange=False,\n trap_divzero=False, divzero=False,\n\ + allow_complex=False,\n rational_division=False,\n\ + allow_release_gil=False)""" + pytest.raises(gmpy2.InvalidOperationError, lambda: mpfr('nan') % 123) + assert repr(ctx) == \ +"""context(precision=53, real_prec=100, imag_prec=200,\n\ + round=RoundToNearest, real_round=Default, imag_round=Default,\n\ + emax=1073741823, emin=-1073741823,\n subnormalize=False,\n\ + trap_underflow=False, underflow=False,\n trap_overflow=False,\ + overflow=False,\n trap_inexact=False, inexact=False,\n\ + trap_invalid=True, invalid=True,\n trap_erange=False,\ + erange=False,\n trap_divzero=False, divzero=False,\n\ + allow_complex=False,\n rational_division=False,\n\ + allow_release_gil=False)""" + set_context(ieee(32)) + ctx = get_context() + ctx.trap_underflow = True + c = mpc(0.1 + 0.1j) + pytest.raises(gmpy2.UnderflowResultError, lambda: c**201) + assert repr(ctx) == \ +"""context(precision=24, real_prec=Default, imag_prec=Default,\n\ + round=RoundToNearest, real_round=Default, imag_round=Default,\n\ + emax=128, emin=-148,\n subnormalize=True,\n\ + trap_underflow=True, underflow=True,\n trap_overflow=False,\ + overflow=False,\n trap_inexact=False, inexact=True,\n\ + trap_invalid=False, invalid=False,\n trap_erange=False,\ + erange=False,\n trap_divzero=False, divzero=False,\n\ + allow_complex=False,\n rational_division=False,\n\ + allow_release_gil=False)""" diff --git a/test/test_functions.py b/test/test_functions.py index 0ecee7c0..8cfe27f4 100644 --- a/test/test_functions.py +++ b/test/test_functions.py @@ -6,16 +6,17 @@ from gmpy2 import (acos, acosh, asin, asinh, atan, atan2, atanh, c_div, c_divmod, c_mod, can_round, check_range, context, copy_sign, cos, cosh, cot, coth, csc, csch, degrees, f2q, f_div, - f_divmod, f_mod, fac, fma, fmma, fmms, fms, from_binary, - get_context, get_emax_max, get_emin_min, get_exp, ieee, inf, - is_bpsw_prp, is_euler_prp, is_extra_strong_lucas_prp, - is_fermat_prp, is_fibonacci_prp, is_finite, is_infinite, - is_lucas_prp, is_nan, is_selfridge_prp, is_strong_bpsw_prp, - is_strong_lucas_prp, is_strong_prp, is_strong_selfridge_prp, - is_zero, maxnum, minnum, mpc, mpfr, mpfr_from_old_binary, - mpq, mpq_from_old_binary, mpz, mpz_from_old_binary, nan, - norm, phase, polar, powmod, powmod_sec, proj, radians, rect, - root, root_of_unity, rootn, sec, sech, set_context, set_exp, + f_divmod, f_mod, fac, fma, fmma, fmms, fms, free_cache, + from_binary, get_context, get_emax_max, get_emin_min, + get_exp, ieee, inf, is_bpsw_prp, is_euler_prp, + is_extra_strong_lucas_prp, is_fermat_prp, is_fibonacci_prp, + is_finite, is_infinite, is_lucas_prp, is_nan, + is_selfridge_prp, is_strong_bpsw_prp, is_strong_lucas_prp, + is_strong_prp, is_strong_selfridge_prp, is_zero, maxnum, + minnum, mpc, mpfr, mpfr_from_old_binary, mpq, + mpq_from_old_binary, mpz, mpz_from_old_binary, nan, norm, + phase, polar, powmod, powmod_sec, proj, radians, rect, root, + root_of_unity, rootn, sec, sech, set_context, set_exp, set_sign, sign, sin, sin_cos, sinh, sinh_cosh, t_div, t_divmod, t_mod, tan, tanh, zero) @@ -156,6 +157,15 @@ def test_get_exp(): pytest.raises(gmpy2.RangeError, lambda: get_exp(mpfr('inf'))) + gmpy2.set_context(context()) + + assert get_exp(mpfr(5.232)) == 3 + + pytest.raises(TypeError, lambda: get_exp(0)) + + assert get_exp(mpfr('inf')) == 0 + assert get_exp(mpfr(0)) == 0 + def test_set_exp(): pytest.raises(ValueError, lambda: set_exp(mpfr('1.0'), int(fac(100)))) @@ -169,6 +179,12 @@ def test_set_exp(): ctx.trap_erange = False assert set_exp(mpfr('1.0'), 1000) == mpfr('1.0') + r = mpfr(4.55) + + assert set_exp(r, 4) == mpfr('9.0999999999999996') + + pytest.raises(TypeError, lambda: set_exp(r, mpz(4))) + def test_can_round(): pytest.raises(TypeError, lambda: can_round(mpfr('1.1'), 10, "spam")) @@ -453,23 +469,6 @@ def test_get_emax_max(): assert get_emax_max() in (4611686018427387903, 1073741823) -def test_get_exp(): - assert get_exp(mpfr(5.232)) == 3 - - pytest.raises(TypeError, lambda: get_exp(0)) - - assert get_exp(mpfr('inf')) == 0 - assert get_exp(mpfr(0)) == 0 - - -def test_set_exp(): - r = mpfr(4.55) - - assert set_exp(r, 4) == mpfr('9.0999999999999996') - - pytest.raises(TypeError, lambda: set_exp(r, mpz(4))) - - def test_set_sign(): r = mpfr(4.55) @@ -919,3 +918,11 @@ def test_t_mod(): assert t_mod(b,-a) == mpz(87) assert t_mod(-b,a) == mpz(-87) assert t_mod(-b,-a) == mpz(-87) + + +def test_get_max_precision(): + assert gmpy2.get_max_precision() > 53 + + +def test_free_cache(): + assert free_cache() is None diff --git a/test/test_mpq.py b/test/test_mpq.py index 23e520b6..4c230054 100644 --- a/test/test_mpq.py +++ b/test/test_mpq.py @@ -133,6 +133,13 @@ def __mpz__(self): return mpz(3) def test_mpq_round(): pytest.raises(TypeError, lambda: mpq(7,3).__round__(4.5)) + q = mpq('4/5') + + assert round(mpq('7/2')) == mpz(4) + assert round(q, 4) == mpq(4,5) + + pytest.raises(TypeError, lambda: round(q, 4, 2)) + @settings(max_examples=1000) @given(integers(), integers(min_value=1)) @@ -555,15 +562,6 @@ def test_mpq_trunc(): assert math.trunc(mpq('7/2')) == mpz(3) -def test_mpq_round(): - q = mpq('4/5') - - assert round(mpq('7/2')) == mpz(4) - assert round(q, 4) == mpq(4,5) - - pytest.raises(TypeError, lambda: round(q, 4, 2)) - - def test_mpq_not(): q = mpq('4/5') @@ -600,6 +598,14 @@ def test_mpq_qdiv(): assert args == (mpq(2), 1/mpq(2)) +def test_mpq_repr(): + assert repr(mpq(11,13)) == 'mpq(11,13)' + + +def test_mpq_str(): + assert str(mpq(11,13)) == '11/13' + + def test_issue_334(): x = mpq(3,2) y = mpq(x,2) From 327ca2be9aa5a145b919ebdd9f4ad04d8f52a244 Mon Sep 17 00:00:00 2001 From: Sergey B Kirpichev Date: Tue, 21 Nov 2023 18:37:48 +0300 Subject: [PATCH 9/9] Don't test dunder methods directly --- src/gmpy2_mpfr_misc.c | 9 ++------- test/test_mpq.py | 2 +- test/test_mpz.py | 1 - 3 files changed, 3 insertions(+), 9 deletions(-) diff --git a/src/gmpy2_mpfr_misc.c b/src/gmpy2_mpfr_misc.c index 13c2eed8..ccdfa8a0 100644 --- a/src/gmpy2_mpfr_misc.c +++ b/src/gmpy2_mpfr_misc.c @@ -710,7 +710,7 @@ GMPy_MPFR_SizeOf_Method(PyObject *self, PyObject *other) } PyDoc_STRVAR(GMPy_doc_method_round10, -"__round__(x[, n = 0]) -> mpfr\n\n" +"x.__round__(n = 0, /) -> mpfr\n\n" "Return x rounded to n decimal digits before (n < 0) or after (n > 0)\n" "the decimal point. Rounds to an integer if n is not specified."); @@ -752,12 +752,7 @@ GMPy_MPFR_Method_Round10(PyObject *self, PyObject *args) return self; } - if (PyTuple_GET_SIZE(args) > 1) { - TYPE_ERROR("__round__() requires 0 or 1 argument"); - return NULL; - } - - if (PyTuple_GET_SIZE(args) == 1) { + if (PyTuple_GET_SIZE(args) >= 1) { digits = PyLong_AsLong(PyTuple_GET_ITEM(args, 0)); if (digits == -1 && PyErr_Occurred()) { TYPE_ERROR("__round__() requires 'int' argument"); diff --git a/test/test_mpq.py b/test/test_mpq.py index 4c230054..f5858a3e 100644 --- a/test/test_mpq.py +++ b/test/test_mpq.py @@ -131,7 +131,7 @@ def __mpz__(self): return mpz(3) def test_mpq_round(): - pytest.raises(TypeError, lambda: mpq(7,3).__round__(4.5)) + pytest.raises(TypeError, lambda: round(mpq(7,3), 4.5)) q = mpq('4/5') diff --git a/test/test_mpz.py b/test/test_mpz.py index 69fb0466..23280645 100644 --- a/test/test_mpz.py +++ b/test/test_mpz.py @@ -580,7 +580,6 @@ def test_mpz_format(): '27', '25', '23', '21', '1z'] raises(ValueError, lambda: a.digits(63)) - raises(TypeError, lambda: a.__format__()) assert '{}'.format(a) == '123' assert '{:d}'.format(a) == '123'