Join GitHub today
GitHub is home to over 31 million developers working together to host and review code, manage projects, and build software together.
Sign upPretty print isn't pretty for floats #29472
Comments
DenisKolodin
changed the title
Pretty print isn't pretty as expected
Pretty print isn't pretty for floats
Oct 30, 2015
This comment has been minimized.
This comment has been minimized.
|
1.2999999999999999 != 1.3. Pretty printing should not be inaccurate by default. However, we've long wanted a mode that prints the shortest exact literal, see #24612 for some discussion. The difference to the default behavior would be that it would use exponential notation when that gives a shorter result. This mode should probably accept a precision Aside:
Wouldn't serialization libraries want accuracy more than pleasing human readers? |
This comment has been minimized.
This comment has been minimized.
|
Thank you for conception.
Not by humans. But problem becoming little deeper... I have some Lua code, which contains parameters that numeric constants. I used to pure Lua to JSON serializer which calls Lua's #24612 doesn't provide a twin for |
This comment has been minimized.
This comment has been minimized.
|
No, AFAIK there hasn't been any activity on a |
This comment has been minimized.
This comment has been minimized.
|
I've found better example: fn main() {
let mut x = 0.1;
for z in (1..100) {
x = x + 0.01;
println!("{}", x);
}
}it prints: 0.11
0.12
0.13
0.14
0.15000000000000002
0.16000000000000003
0.17000000000000004
0.18000000000000005
0.19000000000000006
0.20000000000000007
0.21000000000000008
0.22000000000000008That's really terrible print ) |
This comment has been minimized.
This comment has been minimized.
|
This is an example of floating point arithmetic being inaccurate. The number really is closer to
Besides, I do not buy that other languages do round by default. Here's Java, JavaScript, Python, Ruby giving identical or very similar output. Either Also, changing the default is tricky because lots of programs rely on the exact current behavior. Rounding the output might not break any programs (though it will make some of them less accurate, if they read the output back in), but as explained above I am opposed to that anyway. |
This comment has been minimized.
This comment has been minimized.
|
I think you are right, |
This comment has been minimized.
This comment has been minimized.
|
I absolutely agree with you that there should be a formatting operator that is prettier and can also round to N decimal digits while remaining pretty. I just don't want it to round by default. |
This comment has been minimized.
This comment has been minimized.
|
cc me |
This comment has been minimized.
This comment has been minimized.
roquendm
commented
Nov 2, 2015
|
If you want to error free load/store floating point via text files and target multiple languages...use hexadecimal. Using decimal is a recipe for pain. |
This comment has been minimized.
This comment has been minimized.
|
It's true that decimal representation of binary floats has many downsides, but unfortunately it is also very convenient for humans. Decimal output must exist, might as well make it as pretty as possible while remaining accurate — to say nothing of output for end users that is never read back in. And the really hard part of the implementation is already solved, loading and storing floating point number is already correct in Rust today. It may have to round when first reading decimal input, but every subsequent load-store cycle preserves the bits exactly. |
This comment has been minimized.
This comment has been minimized.
|
@rkruppe I had assumed that the suggestion to use hexadecimal was a response to the scenario given above where one is trying to serialize data between Lua and Rust. (But then again, it was unclear whom @roquendm 's comment was actually directed at... the "and target multiple languages" part was what made me think the text was targetted at @DenisKolodin ) |
This comment has been minimized.
This comment has been minimized.
The discussion on #24612 did (in a comment) mention how we might want to make But its not clear how far we would actually want to go with this. It would probably better to allocate a separate format modifier for this purpose, e.g. |
This comment has been minimized.
This comment has been minimized.
|
Since |
This comment has been minimized.
This comment has been minimized.
roquendm
commented
Nov 2, 2015
|
Indeed my comment was "if one wants to (as simply as possible) be bit-exact across all languages which might read/write the data in a text based format" then use hex floats, |
steveklabnik
added
the
A-libs
label
Nov 11, 2015
huonw
added
I-nominated
T-libs
labels
Jan 6, 2016
This comment has been minimized.
This comment has been minimized.
|
Nominating to discuss:
I'm not a huge fan of 1, but 2 doesn't seem crazy... although 3 and/or people just using e.g. |
This comment has been minimized.
This comment has been minimized.
|
I see in the doc that: What about to use println!("{:-}", 1.2999999999999999);
// 1.3
println!("{:-?}", 1.2999999999999999);
// 1.3 |
This comment has been minimized.
This comment has been minimized.
|
I'm not sure what you're saying here, can't the @DenisKolodin Another thing that bugs me about a direct
This is pretty much what C's NB: I would also prefer ordinary |
aturon
removed
the
I-nominated
label
Jan 8, 2016
This comment has been minimized.
This comment has been minimized.
|
Libs team consensus: any of the changes being discussed here should go through the RFC process. The team would be wiling to consider an RFC for any of the options @huonw mentioned, but would be particularly keen for either option 2 or 3. |
DenisKolodin commentedOct 30, 2015
The following code:
prints:
C behaviour:
prints:
1.3With Rust everything works like f, but not like g.
Is that really no way to get behaviour like g option of
printf?It's highly important feature for serialization libs.
rustc 1.6.0-nightly (8ca0acc 2015-10-28)