8

How do I get a floating point number as a string without the exponent notation, that is, a number that ends in "e-10" or similar? I discovered to_s returns the number with the exponent notation.

ms = 1457000.0000000002 % 1000 # => 2.3283064365386963e-10
ms.to_s                        # => "2.3283064365386963e-10"

I would like to get "0.0000000002", but I don't get it right.

If I use my example above and evaluate "%f" % ms, I get "0.000000", which is much different from "0.0000000002".

sawa
  • 165,429
  • 45
  • 277
  • 381
  • Possible duplicate of [Ruby: Controlling printing in scientific notation](https://stackoverflow.com/questions/1189618/ruby-controlling-printing-in-scientific-notation) – moveson Sep 25 '17 at 22:47
  • That solution doesn't wokr for me, tho. If you use my example above and run "%f" % ms, you get "0.000000", which is much different than "0.0000000002". –  Sep 25 '17 at 22:57
  • Well, technically, it's not *much* different, but may not reflect the accuracy you want. – Dave Newton Sep 25 '17 at 23:18
  • _"I would like to get 0.0000000002"_ – why do you want 10 decimal places and not 12 or 15 or 32? – Stefan Oct 16 '17 at 11:59

2 Answers2

2

I think it'd still work if you specify the number of decimal places (DP) %f. Take your example for instance, the output is an exponent of e-10 thus would be accurate if you specify the DP to 10. Here's a specific:

ms = 1457000.0000000002
secs, ms = ms.divmod(1000)
my_answer = '%.10f' % ms

Your output will be => "0.0000000002"

Ian Shiundu
  • 96
  • 1
  • 8
  • 4
    Thanks. What if I don't know the number of decimal places in advance? –  Sep 26 '17 at 00:02
0

This appears to be a duplicate of this issue:

Force Ruby to not output a float in standard form / scientific notation / exponential notation

You can use sprintf to print the formatted number:

ms = 1457000.0000000002
sprintf("%.10f", ms)
 => "1457000.0000000002"

It's important to note that floating point numbers are not perfectly precise - so if you tell sprintf to display more digits, say 16, you will see this imprecision:

sprintf("%.16f", ms)
=> "1457000.0000000002328306"

A trick for forcing the precision is to use to_r to convert the value to a Rational:

ms = '1457000.0000000002'.to_r
=> (7285000000000001/5000000000)
sprintf("%.16f", ms)
=> "1457000.0000000002000000"
Fred Willmore
  • 4,386
  • 1
  • 27
  • 36