[pypy-commit] pypy py3.6: Add Decimal.as_integer_ratio()
amauryfa
pypy.commits at gmail.com
Mon Dec 11 17:18:59 EST 2017
Author: Amaury Forgeot d'Arc <amauryfa at gmail.com>
Branch: py3.6
Changeset: r93375:5b8174a4dd1d
Date: 2017-12-11 19:47 +0100
http://bitbucket.org/pypy/pypy/changeset/5b8174a4dd1d/
Log: Add Decimal.as_integer_ratio()
diff --git a/lib_pypy/_decimal.py b/lib_pypy/_decimal.py
--- a/lib_pypy/_decimal.py
+++ b/lib_pypy/_decimal.py
@@ -448,6 +448,36 @@
return DecimalTuple(sign, coeff, expt)
+ def as_integer_ratio(self):
+ "Convert a Decimal to its exact integer ratio representation"
+ if _mpdec.mpd_isspecial(self._mpd):
+ if _mpdec.mpd_isnan(self._mpd):
+ raise ValueError("cannot convert NaN to integer ratio")
+ else:
+ raise OverflowError("cannot convert Infinity to integer ratio")
+
+ context = getcontext()
+ tmp = Decimal._new_empty()
+ with _CatchStatus(context) as (ctx, status_ptr):
+ _mpdec.mpd_qcopy(tmp._mpd, self._mpd, status_ptr)
+ exp = tmp._mpd.exp if tmp else 0
+ tmp._mpd.exp = 0
+
+ # context and rounding are unused here: the conversion is exact
+ numerator = tmp._to_int(_mpdec.MPD_ROUND_FLOOR)
+
+ exponent = 10 ** abs(exp)
+ if exp >= 0:
+ numerator *= exponent
+ denominator = 1
+ else:
+ denominator = exponent
+ gcd = _math.gcd(numerator, denominator)
+ numerator //= gcd
+ denominator //= gcd
+
+ return numerator, denominator
+
def _convert_for_comparison(self, other, op):
if isinstance(other, Decimal):
return self, other
More information about the pypy-commit
mailing list