山本です。 >コミットは明日の正午を予定しています。問題がありましたら、よろしくお願いします。 strtod は "INF" じゃなくて "INFINITY" でも無限大として解釈するんですね _no これで晴れて問題なくなりました。 少し自信がなくなったので、コミットは明日の深夜にします。 ////////////////////////////// // パッチ後 irb(main):004:0> a = 1.0 / 0.0 => Infinity irb(main):005:0> a.to_s.to_f => Infinity irb(main):006:0> Float(a.to_s) => Infinity Index: util.c =================================================================== RCS file: /var/cvs/src/ruby/util.c,v retrieving revision 1.43 diff -u -w -b -p -r1.43 util.c --- util.c 14 May 2004 03:17:29 -0000 1.43 +++ util.c 12 Jul 2004 10:17:55 -0000 @@ -750,6 +750,7 @@ ruby_strtod(string, endPtr) * in string. */ const char *pExp; /* Temporarily holds location of exponent * in string. */ + int frac1, frac2; /* * Strip off leading blanks and check for a sign. @@ -772,6 +773,26 @@ ruby_strtod(string, endPtr) } /* + * Check for NaN and Inf. + */ + + if (strncasecmp(p, "NAN", 3) == 0) { + p += 3; + fraction = 0.0 / 0.0; + goto exit; + } + if (strncasecmp(p, "INFINITY", 8) == 0) { + p += 8; + fraction = 1.0 / 0.0; + goto exit; + } + if (strncasecmp(p, "INF", 3) == 0) { + p += 3; + fraction = 1.0 / 0.0; + goto exit; + } + + /* * Count the number of digits in the mantissa * and also locate the decimal point. */ @@ -812,8 +833,7 @@ ruby_strtod(string, endPtr) fracExp += (mantSize - 18); mantSize = 18; } - { - int frac1, frac2; + frac1 = 0; for ( ; mantSize > 9; mantSize -= 1) { c = *p; @@ -920,12 +940,11 @@ ruby_strtod(string, endPtr) else { fraction += frac2 * dblExp; } - } + exit: if (endPtr != NULL) { *endPtr = (char *) p; } - if (sign) { return -fraction; } Index: test_float.rb =================================================================== RCS file: /var/cvs/src/ruby/test/ruby/test_float.rb,v retrieving revision 1.10 diff -u -w -b -p -r1.10 test_float.rb --- test_float.rb 15 May 2004 08:54:23 -0000 1.10 +++ test_float.rb 12 Jul 2004 11:01:42 -0000 @@ -52,6 +52,25 @@ class TestFloat < Test::Unit::TestCase assert_equal(a == b, b == a) end + def strtod_nan(s) + a = Float(s) + assert(a.nan?) + a = Float("+" + s) + assert(a.nan?) + a = Float("-" + s) + assert(a.nan?) + end + def strtod_inf(s) + a = Float(s) + assert(a.infinite?) + assert(a > 0) + a = Float("+" + s) + assert(a.infinite?) + assert(a > 0) + a = Float("-" + s) + assert(a.infinite?) + assert(a < 0) + end def test_strtod a = Float("0") assert(a.abs < Float::EPSILON) @@ -67,6 +86,15 @@ class TestFloat < Test::Unit::TestCase assert(a != 0.0) a = Float("-0." + "00" * Float::DIG + "1") assert(a != 0.0) + strtod_nan("NAN") + strtod_nan("NaN") + strtod_nan("nan") + strtod_inf("INF") + strtod_inf("Inf") + strtod_inf("inf") + strtod_inf("INFINITY") + strtod_inf("Infinity") + strtod_inf("infinity") # add expected behaviour here. end end