首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何处理作为小数的无限重复的数字?

问如何处理作为小数的无限重复的数字?
EN

Stack Overflow用户
提问于 2013-04-19 07:07:20
回答 4查看 3.1K关注 0票数 10

当除法产生一个无限重复的数字时,这个数字显然会被截断以适应小数的大小。因此,1/3就变成了0.3333333333333333333。如果我们将这个数字乘以3,我们得到的结果是0.999999999999999999,而不是1,如果分数的真值被保留下来的话。

这是MSDN文章中关于decimal的代码示例:

代码语言:javascript
复制
decimal dividend = Decimal.One;
decimal divisor = 3;
// The following displays 0.9999999999999999999999999999 to the console
Console.WriteLine(dividend/divisor * divisor); 

在将值0.9999999999999999999与1进行相等比较时,这会导致问题。在没有精度损失的情况下,它们将是相等的,但当然在这种情况下,比较将导致错误。

人们通常是如何处理这个问题的?除了定义每个比较的误差范围之外,还有更优雅的解决方案吗?

EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2013-04-19 07:31:11

这是一个非常古老且广为人知的数值计算问题。您已经说过,您正在寻找一种解决方案,而不是定义每个比较的误差范围。我想到的一种方法是先在内存中构建数学表达式树,然后再进行计算。有了这一点,我们可以在进行计算之前使用一些已知规则进行一些简化。规则如下:

  • 删除分数的分子和分母中的相等数字如果它们不是零,则数字的平方根是数字itself
  • ...

因此,不是将1/3存储在等于0.33333的十进制/双精度值中……我们可以存储Fraction(1, 3)的一个实例。然后,我们可以定义所有其他类似的表达式来构建表达式,而不是进行计算。最后,我们可以先用上面的规则简化表达式,然后计算结果。

我在网上简单地搜索了一下,想找到可以这样做的库,但是还没有找到。但我相信可以找到一些适用于其他语言/平台甚至.NET的。

请注意,上述方法最终只是得到了更好的结果,但并没有解决数值计算本质上的这个问题。

票数 5
EN

Stack Overflow用户

发布于 2013-04-19 07:43:00

正如你所提到的,使用浮点数的计算结果必须‘适合’到浮点表示中。这就是为什么精确比较不是一个好主意--需要一定的容忍度。所以应该使用Math.Abs(x - y) < tolerance,而不是x == y。

票数 2
EN

Stack Overflow用户

发布于 2013-04-19 07:34:41

欢迎来到浮点算术之痛。

当然,您真正想要的是一个有理数类和库。这里是C#的一个开始,尽管我不知道它有多完整(可能不是很完整):

http://www.codeproject.com/Articles/88980/Rational-Numbers-NET-4-0-Version-Rational-Computin

在C/C++中有一些,但同样,不知道它们有多有用/多完整。

对于浮点数:

请看一些参考资料。首先,David Goldberg的经典著作“每个计算机科学家都应该知道浮点算术”。摘要如下:

浮点运算被许多人认为是深奥的学科。这相当令人惊讶,因为浮点在计算机系统中无处不在:几乎每种语言都有浮点数据类型;从PC到超级计算机的计算机都有浮点加速器;大多数编译器将时不时地被调用来编译浮点算法;并且几乎每个操作系统都必须响应浮点异常,例如overflow。本文提供了一个关于浮点方面的教程,这些方面对计算机系统的设计者有直接的影响。它从浮点表示和舍入误差的背景开始,继续讨论IEEE浮点标准,并以计算机系统构建者如何更好地支持浮点的示例结束。

您可以从以下几个位置免费下载该论文的编辑版本:

上找到

​

而且,原版应该在有所有书籍的大砖房里随时都能买到。完整的引用是

以上是

新闻的大卫·戈德堡带来的报道。1991年。每个计算机科学家都应该知道的浮点算术。ACM Comput。Surv。23,1(1991年3月),5-48。DOI=10.1145/103162.103163 http://doi.acm.org/10.1145/103162.103163

然后看看这些资源:

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/16094577

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档