aboutsummaryrefslogtreecommitdiffstats
path: root/numeric.c
diff options
context:
space:
mode:
authormrkn <mrkn@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2016-11-11 15:55:30 +0000
committermrkn <mrkn@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2016-11-11 15:55:30 +0000
commit944e6a2804e7d3961964c586694d16ce036da55d (patch)
tree307f02a0d50d4ffdb9e82df1c345d072527b2b14 /numeric.c
parent8492e990ab03eb8eb4415ac5ab05fb024349d7a3 (diff)
downloadruby-944e6a2804e7d3961964c586694d16ce036da55d.tar.gz
rational.c: avoid needless object allocation with nurat_to_double
* rational.c (nurat_to_double): introduce to convert rational to double without object allocation. * rational.c (rb_rational_plus, nurat_{sub,mul,to_f}): rewrite by using nurat_to_double. * bignum.c (rb_big_fdiv_double): introduce to calculate fdiv and return the result as a double value. * bignum.c (big_fdiv{,_int,_float}): change the return types for implementing rb_big_fdiv_double. * bignum.c (rb_big_fdiv): rewrite by using rb_big_fdiv_double. * numeric.c (rb_int_fdiv_double): introduce to calculate fdiv and return the result as a double value. * numeric.c (fix_fdiv_double): rewrite from fix_fdiv to return the result as a double value. * numeric.c (rb_int_fdiv): rewrite by using rb_int_fdiv_double. * internal.h (rb_{big,int}_fdiv_double): exported. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@56719 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'numeric.c')
-rw-r--r--numeric.c53
1 files changed, 31 insertions, 22 deletions
diff --git a/numeric.c b/numeric.c
index e2c26f54c2..8df969eb49 100644
--- a/numeric.c
+++ b/numeric.c
@@ -3549,6 +3549,35 @@ rb_int_mul(VALUE x, VALUE y)
return rb_num_coerce_bin(x, y, '*');
}
+static double
+fix_fdiv_double(VALUE x, VALUE y)
+{
+ if (FIXNUM_P(y)) {
+ return (double)FIX2LONG(x) / (double)FIX2LONG(y);
+ }
+ else if (RB_TYPE_P(y, T_BIGNUM)) {
+ return rb_big_fdiv_double(rb_int2big(FIX2LONG(x)), y);
+ }
+ else if (RB_TYPE_P(y, T_FLOAT)) {
+ return (double)FIX2LONG(x) / RFLOAT_VALUE(y);
+ }
+ else {
+ return RFLOAT_VALUE(rb_num_coerce_bin(x, y, rb_intern("fdiv")));
+ }
+}
+
+double
+rb_int_fdiv_double(VALUE x, VALUE y)
+{
+ if (FIXNUM_P(x)) {
+ return fix_fdiv_double(x, y);
+ }
+ else if (RB_TYPE_P(x, T_BIGNUM)) {
+ return rb_big_fdiv_double(x, y);
+ }
+ return NAN;
+}
+
/*
* Document-method: Integer#fdiv
* call-seq:
@@ -3564,31 +3593,11 @@ rb_int_mul(VALUE x, VALUE y)
*
*/
-static VALUE
-fix_fdiv(VALUE x, VALUE y)
-{
- if (FIXNUM_P(y)) {
- return DBL2NUM((double)FIX2LONG(x) / (double)FIX2LONG(y));
- }
- else if (RB_TYPE_P(y, T_BIGNUM)) {
- return rb_big_fdiv(rb_int2big(FIX2LONG(x)), y);
- }
- else if (RB_TYPE_P(y, T_FLOAT)) {
- return DBL2NUM((double)FIX2LONG(x) / RFLOAT_VALUE(y));
- }
- else {
- return rb_num_coerce_bin(x, y, rb_intern("fdiv"));
- }
-}
-
VALUE
rb_int_fdiv(VALUE x, VALUE y)
{
- if (FIXNUM_P(x)) {
- return fix_fdiv(x, y);
- }
- else if (RB_TYPE_P(x, T_BIGNUM)) {
- return rb_big_fdiv(x, y);
+ if (RB_INTEGER_TYPE_P(x)) {
+ return DBL2NUM(rb_int_fdiv_double(x, y));
}
return Qnil;
}