realfield.py 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132
  1. """Implementation of :class:`RealField` class. """
  2. from sympy.core.numbers import Float
  3. from sympy.polys.domains.field import Field
  4. from sympy.polys.domains.simpledomain import SimpleDomain
  5. from sympy.polys.domains.characteristiczero import CharacteristicZero
  6. from sympy.polys.domains.mpelements import MPContext
  7. from sympy.polys.polyerrors import CoercionFailed
  8. from sympy.utilities import public
  9. @public
  10. class RealField(Field, CharacteristicZero, SimpleDomain):
  11. """Real numbers up to the given precision. """
  12. rep = 'RR'
  13. is_RealField = is_RR = True
  14. is_Exact = False
  15. is_Numerical = True
  16. is_PID = False
  17. has_assoc_Ring = False
  18. has_assoc_Field = True
  19. _default_precision = 53
  20. @property
  21. def has_default_precision(self):
  22. return self.precision == self._default_precision
  23. @property
  24. def precision(self):
  25. return self._context.prec
  26. @property
  27. def dps(self):
  28. return self._context.dps
  29. @property
  30. def tolerance(self):
  31. return self._context.tolerance
  32. def __init__(self, prec=_default_precision, dps=None, tol=None):
  33. context = MPContext(prec, dps, tol, True)
  34. context._parent = self
  35. self._context = context
  36. self.dtype = context.mpf
  37. self.zero = self.dtype(0)
  38. self.one = self.dtype(1)
  39. def __eq__(self, other):
  40. return (isinstance(other, RealField)
  41. and self.precision == other.precision
  42. and self.tolerance == other.tolerance)
  43. def __hash__(self):
  44. return hash((self.__class__.__name__, self.dtype, self.precision, self.tolerance))
  45. def to_sympy(self, element):
  46. """Convert ``element`` to SymPy number. """
  47. return Float(element, self.dps)
  48. def from_sympy(self, expr):
  49. """Convert SymPy's number to ``dtype``. """
  50. number = expr.evalf(n=self.dps)
  51. if number.is_Number:
  52. return self.dtype(number)
  53. else:
  54. raise CoercionFailed("expected real number, got %s" % expr)
  55. def from_ZZ(self, element, base):
  56. return self.dtype(element)
  57. def from_ZZ_python(self, element, base):
  58. return self.dtype(element)
  59. def from_QQ(self, element, base):
  60. return self.dtype(element.numerator) / element.denominator
  61. def from_QQ_python(self, element, base):
  62. return self.dtype(element.numerator) / element.denominator
  63. def from_ZZ_gmpy(self, element, base):
  64. return self.dtype(int(element))
  65. def from_QQ_gmpy(self, element, base):
  66. return self.dtype(int(element.numerator)) / int(element.denominator)
  67. def from_AlgebraicField(self, element, base):
  68. return self.from_sympy(base.to_sympy(element).evalf(self.dps))
  69. def from_RealField(self, element, base):
  70. if self == base:
  71. return element
  72. else:
  73. return self.dtype(element)
  74. def from_ComplexField(self, element, base):
  75. if not element.imag:
  76. return self.dtype(element.real)
  77. def to_rational(self, element, limit=True):
  78. """Convert a real number to rational number. """
  79. return self._context.to_rational(element, limit)
  80. def get_ring(self):
  81. """Returns a ring associated with ``self``. """
  82. return self
  83. def get_exact(self):
  84. """Returns an exact domain associated with ``self``. """
  85. from sympy.polys.domains import QQ
  86. return QQ
  87. def gcd(self, a, b):
  88. """Returns GCD of ``a`` and ``b``. """
  89. return self.one
  90. def lcm(self, a, b):
  91. """Returns LCM of ``a`` and ``b``. """
  92. return a*b
  93. def almosteq(self, a, b, tolerance=None):
  94. """Check if ``a`` and ``b`` are almost equal. """
  95. return self._context.almosteq(a, b, tolerance)
  96. RR = RealField()