程序中两个Double类型相加出现误差的解决办法

所属分类: 软件编程 / C#教程 阅读数: 135
收藏 0 赞 0 分享

今天在自己做的系统中,发现了一个奇怪的现象:几个Double类型的数据相加,到最后得出的金额比正确数值总是少了几毛钱。以为是程序里的计算方法有问题,可是排查了很多地方,始终没有找到问题出在哪里。最后干脆把计算方法一句一句拆分,得到了最后最简单的一步,就是把两个具体的数值相加,但是最后的结果居然还是错误的。比如,现在已经到了最简单的一步:

复制代码 代码如下:

double n = 171.6;
double m = 28.17;
double k = n + m;

  按理说k的值应该是199.77,但其实得到的居然是199.76999999999998。

     我们的系统里有保留小数位数为4位,按理是可以四舍五入成199.77的。但是因为有做金额的合计,是几十甚至几百个数据的相加,由于每两个数相加的时候都可能产生上述误差,因此最后得到的结果已经有了近0.7的误差,就算再四舍五入也于事无补了。

     上网查了一下相关资料,觉得CSDN论坛里的这个帖子的解释还是比较详细的:http://bbs.csdn.net/topics/300023952,大意是说由于运算的时候进行了进制的转换造成的(见8楼回复),所有的精度类型在几乎所有语言下都有这个问题。比较有效的解决办法是使用BigDecimal(见14楼回复),但是我个人认为那个BigDecimal的解决办法太麻烦了,至少对于我的系统来说是这样。还不如每加一次之后都进行一次字符串转换,保留有效的小数位数,比如,上述语句可以改写成:

复制代码 代码如下:

double n = 171.6;
double m = 28.17;
//double k = n + m;
String kn = (n + m).ToString("N4");    //保留4位小数
double k = Convert.ToDouble(kn);

  也就是说,在String kn这一步,就已经把误差调整好了,得到的k值就是正确的了。这样每次相加都处理一下误差,无论要算多少个数据的合计也不用担心会出现误差过大的情况了。

    当然最好是把这种处理方法做成一个公用方法,专门用来处理两个数的相加。

更多精彩内容其他人还在看

C# 大小写转换(金额)实例代码

C# 大小写转换(金额)实例代码,需要的朋友可以参考一下
收藏 0 赞 0 分享

C# WinForm中Panel实现用鼠标操作滚动条的实例方法

由于在WinForm中Panel不能直接响应鼠标的滚动事件,只好采用捕获窗体的滚动事件。
收藏 0 赞 0 分享

C#访问应用程序配置文件的方法

C#访问应用程序配置文件的方法,需要的朋友可以参考一下
收藏 0 赞 0 分享

C#读写文件的方法汇总

C#读写文件的方法汇总,需要的朋友可以参考一下
收藏 0 赞 0 分享

C#计算代码执行时间的方法

在一些测试工作时我们需要获得高精度的代码执行时间以比较其效率。
收藏 0 赞 0 分享

C# 动画窗体(AnimateWindow)的小例子

C# 动画窗体(AnimateWindow)的小例子,需要的朋友可以参考一下
收藏 0 赞 0 分享

C# zxing二维码写入的实例代码

C# zxing二维码写入的实例代码,需要的朋友可以参考一下
收藏 0 赞 0 分享

c#判断输入的是不是数字的小例子

c#判断输入的是不是数字的小例子,需要的朋友可以参考一下
收藏 0 赞 0 分享

c# 深拷贝与浅拷贝的区别分析及实例

浅拷贝(影子克隆):只复制对象的基本类型,对象类型,仍属于原来的引用. 深拷贝(深度克隆):不紧复制对象的基本类,同时也复制原对象中的对象.就是说完全是新对象产生的.
收藏 0 赞 0 分享

C#利用com操作excel释放进程的解决方法

最近利用Microsoft.Office.Interop.Excel.Application读取一个excel后,进程中一直存在excel,在网上找了一阵子,其中有几个解决方案
收藏 0 赞 0 分享
查看更多