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 "<stdin>", line 1, in <module>
TypeError: unsupported operand type(s) for +: 'mpfr' and 'str'
>>> 'b'+a
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
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 "<stdin>", line 1, in <module>
TypeError: unsupported operand type(s) for -: 'mpfr' and 'str'
>>> 'b'-a
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
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 "<stdin>", line 1, in <module>
TypeError: unsupported operand type(s) for /: 'mpfr' and 'str'
>>> get_context().div(b, 'str')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
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 "<stdin>", line 1, in <module>
gmpy2.DivisionByZeroError: mod() modulo by zero
>>> b % mpz(0)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
gmpy2.DivisionByZeroError: mod() modulo by zero
>>> get_context().mod(b, 0)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
gmpy2.DivisionByZeroError: mod() modulo by zero
>>> get_context().mod(b, mpz(0))
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
gmpy2.DivisionByZeroError: mod() modulo by zero
>>> b % mpfr(0)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
gmpy2.DivisionByZeroError: mod() modulo by zero
>>> get_context().mod(b, mpfr(0))
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
gmpy2.DivisionByZeroError: mod() modulo by zero
>>> get_context().trap_divzero = False
>>> b % 'str'
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: unsupported operand type(s) for %: 'mpfr' and 'str'
>>> get_context().mod(b,'str')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: mod() argument type not supported
>>> b % mpc(3, 5)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
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 "<stdin>", line 1, in <module>
gmpy2.InvalidOperationError: invalid operation
>>> a % mpfr('nan')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
gmpy2.InvalidOperationError: invalid operation
>>> mpfr('inf') % a
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
gmpy2.InvalidOperationError: mod() invalid operation
>>> a % mpfr('inf')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
gmpy2.InvalidOperationError: mod() invalid operation
>>> get_context().trap_invalid = False
>>> get_context().mod(a, b, 5)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: mod() requires 2 arguments
>>> 1
1

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

