@@ -271,34 +271,8 @@ public static IRubyObject induced_from(ThreadContext context, IRubyObject recv,
271271 @ JRubyMethod (name = {"to_s" , "inspect" })
272272 @ Override
273273 public IRubyObject to_s (ThreadContext context ) {
274- if (Double .isInfinite (value )) {
275- return newSharedString (context , value < 0 ? NEGATIVE_INFINITY_TO_S_BYTELIST : POSITIVE_INFINITY_TO_S_BYTELIST );
276- }
277- if (Double .isNaN (value )) return newSharedString (context , NAN_TO_S_BYTELIST );
278-
279- ByteList buf = new ByteList ();
280- // Under 1.9, use full-precision float formatting (JRUBY-4846).
281- // Double-precision can represent around 16 decimal digits;
282- // we use 20 to ensure full representation.
283- Sprintf .sprintf (buf , Locale .US , "%#.20g" , this );
284- int e = buf .indexOf ('e' );
285- if (e == -1 ) e = buf .getRealSize ();
286- ASCIIEncoding ascii = ASCIIEncoding .INSTANCE ;
287-
288- if (!ascii .isDigit (buf .get (e - 1 ))) {
289- buf .setRealSize (0 );
290- Sprintf .sprintf (buf , Locale .US , "%#.14e" , this );
291- e = buf .indexOf ('e' );
292- if (e == -1 ) e = buf .getRealSize ();
293- }
294-
295- int p = e ;
296- while (buf .get (p - 1 ) == '0' && ascii .isDigit (buf .get (p - 2 ))) p --;
297- System .arraycopy (buf .getUnsafeBytes (), e , buf .getUnsafeBytes (), p , buf .getRealSize () - e );
298- buf .setRealSize (p + buf .getRealSize () - e );
299-
300- buf .setEncoding (USASCIIEncoding .INSTANCE );
301-
274+ ByteList buf = new ByteList (24 );
275+ formatFloat (this , buf );
302276 return newString (context , buf );
303277 }
304278
@@ -802,7 +776,7 @@ public IRubyObject rationalize(ThreadContext context, IRubyObject[] args) {
802776
803777 RubyInteger two_times_f = (RubyInteger ) rf .op_mul (context , 2 );
804778 den = (RubyInteger ) one .op_lshift (context , one .op_minus (context , n ));
805-
779+
806780 a = RubyRational .newRationalRaw (runtime , two_times_f .op_minus (context , 1 ), den );
807781 b = RubyRational .newRationalRaw (runtime , two_times_f .op_plus (context , 1 ), den );
808782 }
@@ -1141,6 +1115,47 @@ private ByteList marshalDump(ThreadContext context) {
11411115 return byteList ;
11421116 }
11431117
1118+ public static ByteList formatFloat (RubyFloat self , ByteList buf ) {
1119+ buf .setRealSize (0 );
1120+
1121+ double value = self .value ;
1122+
1123+ if (Double .isInfinite (value )) {
1124+ buf .append (value < 0
1125+ ? NEGATIVE_INFINITY_TO_S_BYTELIST
1126+ : POSITIVE_INFINITY_TO_S_BYTELIST );
1127+ buf .setEncoding (USASCIIEncoding .INSTANCE );
1128+ return buf ;
1129+ }
1130+
1131+ if (Double .isNaN (value )) {
1132+ buf .append (NAN_TO_S_BYTELIST );
1133+ buf .setEncoding (USASCIIEncoding .INSTANCE );
1134+ return buf ;
1135+ }
1136+
1137+ Sprintf .sprintf (buf , Locale .US , "%#.20g" , self );
1138+
1139+ int e = buf .indexOf ('e' );
1140+ if (e == -1 ) e = buf .getRealSize ();
1141+ ASCIIEncoding ascii = ASCIIEncoding .INSTANCE ;
1142+
1143+ if (!ascii .isDigit (buf .get (e - 1 ))) {
1144+ buf .setRealSize (0 );
1145+ Sprintf .sprintf (buf , Locale .US , "%#.14e" , self );
1146+ e = buf .indexOf ('e' );
1147+ if (e == -1 ) e = buf .getRealSize ();
1148+ }
1149+
1150+ int p = e ;
1151+ while (buf .get (p - 1 ) == '0' && ascii .isDigit (buf .get (p - 2 ))) p --;
1152+ System .arraycopy (buf .getUnsafeBytes (), e , buf .getUnsafeBytes (), p , buf .getRealSize () - e );
1153+ buf .setRealSize (p + buf .getRealSize () - e );
1154+
1155+ buf .setEncoding (USASCIIEncoding .INSTANCE );
1156+ return buf ;
1157+ }
1158+
11441159 @ Deprecated (since = "10.0.0.0" , forRemoval = true )
11451160 @ SuppressWarnings ("removal" )
11461161 public static void marshalTo (RubyFloat aFloat , org .jruby .runtime .marshal .MarshalStream output ) throws java .io .IOException {
0 commit comments