float_to_list vs io:format ~w
Mon Jun 28 11:33:34 CEST 2021
Short answer: because the BIF use the libc sprintf, which does not support
the format offered by io:format
Slightly more complex answer: it does not yet, but it is coming, PR at
The io:format format is known as "shortest round-trip conversion". It has
the advantage of always giving the shortest string while keeping perfect
precision, making it both better for external data exchange (less bytes
used) and for human readability.
It has historically been a problem. We had no fast algorithm to generate
that format, even less an algorithm that does not need arbitrarily large
integers. So it is not implemented in the libcs anywhere, as it was really
complex and expensive. It is not in the C spec. We only have %g which is...
its own mess.
This changed a few years ago thanks to Ryu, an algorithm presented by Ulf
Adams in 2018. https://github.com/ulfjack/ryu
I have been working for 9 months bringing Ryu to OTP, which is slowly
happening. Hopefully before OTP 25.
Getting it in the libc will probably take a few decades, seeing how much
dev cycle they get for the amount of legacy they deal with.
Hope that answer the question ? Always available if someone want to dig
Schedule a meeting with me
On Mon, 28 Jun 2021 at 11:23, Viktor Söderqvist <viktor@REDACTED>
> Apparently, float_to_binary/1 and float_to_list/1 return a different
> textual representation than io:format("~w", [Float]) and the shell.
> Eshell V11.1.8 (abort with ^G)
> 1> float_to_list(10.2).
> 2> 1.01999999999999992895e+01.
> 3> io:format("~w~n", [10.2]).
> 4> 1.01999999999999992895e+01 =:= 10.2.
> Apparently, both are correct textual representations of the same
> floating point value. Why don't they use the same algorithm?
-------------- next part --------------
An HTML attachment was scrubbed...
More information about the erlang-questions