Author: Amaury Forgeot d'Arc <amaur...@gmail.com> Branch: decimal-libmpdec Changeset: r71622:7b1c4d62bf95 Date: 2014-05-19 00:20 +0200 http://bitbucket.org/pypy/pypy/changeset/7b1c4d62bf95/
Log: Add Decimal.to_integral*() diff --git a/pypy/module/_decimal/interp_decimal.py b/pypy/module/_decimal/interp_decimal.py --- a/pypy/module/_decimal/interp_decimal.py +++ b/pypy/module/_decimal/interp_decimal.py @@ -313,6 +313,35 @@ status_ptr) return w_result + # Unary arithmetic functions, optional context arg + + def to_integral_w(self, space, w_rounding=None, w_context=None): + context = interp_context.ensure_context(space, w_context) + w_workctx = context.copy_w(space) + if not space.is_none(w_rounding): + w_workctx.set_rounding(space, w_rounding) + w_result = W_Decimal.allocate(space) + with context.catch_status(space) as (ctx, status_ptr): + # We round with the temporary context, but set status and + # raise errors on the global one. + rmpdec.mpd_qround_to_int(w_result.mpd, self.mpd, + w_workctx.ctx, status_ptr) + return w_result + + def to_integral_exact_w(self, space, w_rounding=None, w_context=None): + context = interp_context.ensure_context(space, w_context) + w_workctx = context.copy_w(space) + if not space.is_none(w_rounding): + w_workctx.set_rounding(space, w_rounding) + w_result = W_Decimal.allocate(space) + with context.catch_status(space) as (ctx, status_ptr): + # We round with the temporary context, but set status and + # raise errors on the global one. + rmpdec.mpd_qround_to_intx(w_result.mpd, self.mpd, + w_workctx.ctx, status_ptr) + return w_result + + # Boolean functions def is_qnan_w(self, space): return space.wrap(bool(rmpdec.mpd_isqnan(self.mpd))) @@ -690,6 +719,10 @@ __rmod__ = interp2app(W_Decimal.descr_rmod), __rdivmod__ = interp2app(W_Decimal.descr_rdivmod), __rpow__ = interp2app(W_Decimal.descr_rpow), + # Unary arithmetic functions, optional context arg + to_integral = interp2app(W_Decimal.to_integral_w), + to_integral_value = interp2app(W_Decimal.to_integral_w), + to_integral_exact = interp2app(W_Decimal.to_integral_exact_w), # copy_sign = interp2app(W_Decimal.copy_sign_w), is_qnan = interp2app(W_Decimal.is_qnan_w), diff --git a/pypy/module/_decimal/test/test_decimal.py b/pypy/module/_decimal/test/test_decimal.py --- a/pypy/module/_decimal/test/test_decimal.py +++ b/pypy/module/_decimal/test/test_decimal.py @@ -758,3 +758,35 @@ d = Decimal( (1, (0, 2, 7, 1), 'F') ) assert d.as_tuple() == (1, (0,), 'F') + def test_c_integral(self): + Decimal = self.decimal.Decimal + Inexact = self.decimal.Inexact + localcontext = self.decimal.localcontext + ROUND_UP = self.decimal.ROUND_UP + + x = Decimal(10) + assert x.to_integral() == 10 + raises(TypeError, x.to_integral, '10') + raises(TypeError, x.to_integral, 10, 'x') + raises(TypeError, x.to_integral, 10) + + assert x.to_integral_value() == 10 + raises(TypeError, x.to_integral_value, '10') + raises(TypeError, x.to_integral_value, 10, 'x') + raises(TypeError, x.to_integral_value, 10) + + assert x.to_integral_exact() == 10 + raises(TypeError, x.to_integral_exact, '10') + raises(TypeError, x.to_integral_exact, 10, 'x') + raises(TypeError, x.to_integral_exact, 10) + + with localcontext() as c: + x = Decimal("99999999999999999999999999.9").to_integral_value(ROUND_UP) + assert x == Decimal('100000000000000000000000000') + + x = Decimal("99999999999999999999999999.9").to_integral_exact(ROUND_UP) + assert x == Decimal('100000000000000000000000000') + + c.traps[Inexact] = True + raises(Inexact, Decimal("999.9").to_integral_exact, ROUND_UP) + _______________________________________________ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit