Home > Software design >  How does the V8 toString(radix) method in Google Chrome or in Node.js handle floating point numbers?
How does the V8 toString(radix) method in Google Chrome or in Node.js handle floating point numbers?

Time:12-16

The method works clearly with integer numbers, e.g.

(25).toString(2)
= '11001'

(25).toString(16)
= '19'

(25).toString(36)
= 'p'

But entering floats results in

(0.1).toString(2)
= '0.0001100110011001100110011001100110011001100110011001101'

(0.1).toString(16)
= '0.1999999999999a'

(0.1).toString(36)
= '0.3lllllllllm'

V8 is said to be an open-source engine. However, I cannot find the exact implementation of this method in the repository in order to understand it. How does the function handle floats?

CodePudding user response:

(V8 developer here.)

@pilchard's link is right; more specifically the function you're looking for is DoubleToRadixCString.

The observation that 0.1 (decimal) is a non-terminating fraction in its binary representation (which is, of course, how doubles are stored inside computers) is a nice illustration of the underlying reason why 0.1 * 3 == 0.30000000000000004: the non-terminating fractions are necessarily cut off at some point, which constitutes a rounding error, and some operations make these rounding errors visible. It's the binary equivalent of a similar effect in decimal: when you represent 1/3 as "0.333333" (arbitrarily choosing 6 digits as the represented length, but if you only cut off after 100 digits that wouldn't really change anything), and multiply that by 3, you get "0.999999", not 1.

  • Related