diff options
author | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2016-11-25 06:28:00 +0000 |
---|---|---|
committer | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2016-11-25 06:28:00 +0000 |
commit | 631dde2572eb78cbf09d73d23a43852ccb199bd1 (patch) | |
tree | d85aad8b66468b69730c9a85362879b56f5aa41a /numeric.c | |
parent | b6d10b6c378edcb88d3238b5c862e585ad9c8b33 (diff) |
round-down
* numeric.c (round_half_down, int_round_half_down): support
round-down mode.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@56897 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'numeric.c')
-rw-r--r-- | numeric.c | 39 |
1 files changed, 39 insertions, 0 deletions
@@ -119,6 +119,31 @@ round_half_up(double x, double s) } static double +round_half_down(double x, double s) +{ + double f, xs = x * s; + +#ifdef HAVE_ROUND + f = round(xs); +#endif + if (x > 0) { +#ifndef HAVE_ROUND + f = ceil(xs); +#endif + if ((double)((f - 0.5) / s) >= x) f -= 1; + x = f; + } + else { +#ifndef HAVE_ROUND + f = floor(xs); +#endif + if ((double)((f + 0.5) / s) <= x) f += 1; + x = f; + } + return x; +} + +static double round_half_even(double x, double s) { double f, d, xs = x * s; @@ -213,6 +238,8 @@ rb_num_get_rounding_option(VALUE opts) case 4: if (rb_memcicmp(s, "even", 4) == 0) return RUBY_NUM_ROUND_HALF_EVEN; + if (strncasecmp(s, "down", 4) == 0) + return RUBY_NUM_ROUND_HALF_DOWN; break; } invalid: @@ -2040,6 +2067,12 @@ int_round_half_up(SIGNED_VALUE x, SIGNED_VALUE y) return (x + y / 2) / y * y; } +static SIGNED_VALUE +int_round_half_down(SIGNED_VALUE x, SIGNED_VALUE y) +{ + return (x + y / 2 - 1) / y * y; +} + static int int_half_p_half_even(VALUE num, VALUE n, VALUE f) { @@ -2052,6 +2085,12 @@ int_half_p_half_up(VALUE num, VALUE n, VALUE f) return int_pos_p(num); } +static int +int_half_p_half_down(VALUE num, VALUE n, VALUE f) +{ + return int_neg_p(num); +} + /* * Assumes num is an Integer, ndigits <= 0 */ |