diff options
author | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2016-08-15 01:59:58 +0000 |
---|---|---|
committer | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2016-08-15 01:59:58 +0000 |
commit | ab65e9d98317afbc43ac1965d3f090571244fe4e (patch) | |
tree | c153e97b4d5954d4d9c0dc778cf237eb31ae0026 | |
parent | dfe1d4fda6521729ff3536b53cb2cdc9a034a015 (diff) |
numeric.c: round_to_nearest
* numeric.c (round_to_nearest): extract and reduce for platforms
where round is not available.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@55897 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r-- | numeric.c | 33 |
1 files changed, 26 insertions, 7 deletions
@@ -92,6 +92,31 @@ round(double x) } #endif +static double +round_to_nearest(double x, double s) +{ + double f, xs = x * s; + +#ifdef HAVE_ROUND + f = round(xs); +#endif + if (x > 0) { +#ifndef HAVE_ROUND + f = floor(xs); +#endif + if ((double)((f + 0.5) / s) <= x) f += 1; + x = f; + } + else { +#ifndef HAVE_ROUND + f = ceil(xs); +#endif + if ((double)((f - 0.5) / s) >= x) f -= 1; + x = f; + } + return x; +} + static VALUE fix_uminus(VALUE num); static VALUE fix_mul(VALUE x, VALUE y); static VALUE fix_lshift(long, unsigned long); @@ -2089,13 +2114,7 @@ flo_round(int argc, VALUE *argv, VALUE num) } if (float_invariant_round(number, ndigits, &num)) return num; f = pow(10, ndigits); - x = round(number * f); - if (x > 0) { - if ((double)((x + 0.5) / f) <= number) x += 1; - } - else { - if ((double)((x - 0.5) / f) >= number) x -= 1; - } + x = round_to_nearest(number, f); return DBL2NUM(x / f); } |