我正在开发一个代码,我必须在文本文件中一次加载存储在每一行中的浮点值...我使用fscanf()将每个数据加载到一个浮点数组中...但是我发现浮点数以不同的方式存储,例如407.18存储为407.179993,414.35存储为414.350006 ...现在我被卡住了,因为数据以它们在文件中的形式存储是绝对重要的但是在这里似乎是不同的,即使基本上是相同的....我如何得到以原始形式存储的数字?
答案 0 :(得分:17)
如果数字以文件中的形式存储是绝对重要的,不要使用浮点值。并非所有小数基数为10的值都可以用二进制精确表示。
有关详细信息,请参阅文章"What Every Computer Scientist Should Know About Floating-Point Arithmetic" [PDF链接]。
您应该以字符串形式或缩放整数存储数字。
答案 1 :(得分:11)
你看到的是正确的,因为浮点不能完全代表许多实数。这是必读的:What Every Computer Scientist Should Know About Floating-Point Arithmetic
答案 2 :(得分:2)
C ++ float
和double
类型表示为IEEE浮点数。有二进制浮点数,而不是小数。它们没有无限的精度,甚至相对“简单”的十进制值在转换为二进制浮点和返回时也会改变。
专注于货币的语言(例如COBOL和PL / I)具有十进制数据类型,这些数据类型使用较慢的表示而没有此问题。在C或C ++中有用于此目的的库,或者如果您不需要太多范围,则可以使用缩放的整数。
答案 3 :(得分:2)
的S factor, 一点澄清:你说“......绝对重要的是,数字存储在文件中的形式” - 这是什么'形式'?我假设一个展示形式?!这是交易:如果你存储在文件407.18中,但它显示为407.179993 - 这是完全正常的和预期的。当您构建sprintf或正在使用的任何格式化打印时,必须指示它限制小数点后的精度。这应该可以解决问题:
#include <stdio.h>
void main(void);
void main()
{
printf("%.2f",407.179993);
}
答案 4 :(得分:0)
您可能希望查看实现具有受控舍入的浮点的现有库。我使用过MPFR。它是快速和开源的。如果你正在处理钱,那么另一个图书馆会更好。
答案 5 :(得分:0)
存储数字的方式有很多种 - 每种方式都有其优点和缺点。
在您的情况下,浮点数不是最佳选择,因为它们不代表大多数实数完全。
缩放整数是常见设计习语的一种情况:与演示文稿分开表示。
确定小数点后您想要多少位数,例如。 123,45中的2位数字。然后,您应该将数字表示为整数12345.无论何时向用户显示值,都应在相关位置插入小数点。
简短InformIT article on Scaled Integers by Danny Kalev
在过度使用缩放的整数之前,请仔细检查问题的域,以断言浮点数中的“松弛”足以使用缩放的整数进行警告。