请问浮点数比较为什么会不准确?

月影 2009-04-12 02:34:39
计算机课程中我们会学到:不能直接用等号比较两个浮点数, 例如 if( .00033434 == .00033434) ;
请问浮点数为什么会不准确呢?
此问题纯属学术讨论, 没有任何其他目的。
...全文
1258 23 打赏 收藏 转发到动态 举报
写回复
用AI写文章
23 条回复
切换为时间正序
请发表友善的回复…
发表回复
深海之蓝 2009-04-13
  • 打赏
  • 举报
回复
[Quote=引用 3 楼 sunny906 的回复:]
因为十进制小数转为二进制可能变为无限小数导致不精确
可以通过相减的差值和约定的精度相比较
例如:
if(fabs(f1-f2) <0.000001)
[/Quote]
正解
wartim 2009-04-13
  • 打赏
  • 举报
回复
这是由于计算机的浮点数格式决定的,从远古时期就有这问题了,
浮点数是由符号位、指数位、数据位构成的,不是像整形那样简单地构建

有篇专门讲浮点数的ieee标准的论文,看晕你

基于IEEE 754的浮点数存储格式分析研究
http://lw.china-b.com/gxlx/20090313/848581_1.html
vrhero 2009-04-13
  • 打赏
  • 举报
回复
基础问题...lz没学过计算机原理?从楼上的答案学过的竟然是少数...
gomoku 2009-04-13
  • 打赏
  • 举报
回复
[Quote=引用 12 楼 gentle_wolf 的回复:]
我要的是产生这个问题的原因。
[/Quote]

数学上浮点数是连续的,是无限的。
而计算机用有限的32位或64位来表示浮点,而32位的最多只能有4G种组合方法,即使是128位,它只能用来表示无限的数字中的某些点。
"某些点"以外的数就无法准确的用计算机浮点数来表示,这就是浮点误差的来源。
OKILOVE 2009-04-13
  • 打赏
  • 举报
回复
http://blog.csdn.net/biblereader/archive/2006/06/21/819428.aspx
“不能直接用等号比较两个浮点数”应该是比较一些特殊的浮点数

浮点数是不可以直接比较大小的,因为是非精确存储,只能设置一个精度,然后在允许误差内的就认为是相等的;对浮点型数比较的时候用==是不对的

#define E 0.000001

fabs((a+b)+c) - ((b+a)+c))<EPSIMON

C/C++语言中,浮点数常量默认就是double。明确指定是float可以使用:0.5f

浮点数也不是绝对不能精确的表示,比如0.5,0.25,0.125等等都是可以精确表示

对于可以精确表示的浮点数来说,==符号也是有意义的 但是对于大多数浮点数来说,是不能精确表示的,考虑到精度问题,两个也许实际不等的数值,比如

10000000.00000001 和 10000000 在pc当中被表示成为相同的数字了

对于确切两个浮点数 a+b 和 b+a 永远是等的

但是 (a+b)+c 和 (a+c)+b 就不一定
OKILOVE 2009-04-13
  • 打赏
  • 举报
回复
http://blog.csdn.net/cppptr/archive/2006/01/08/573372.aspx
http://blog.csdn.net/welman00chijian/archive/2006/02/21/604973.aspx
lz可以看看这个,我也受教了一次~
gjw_8888 2009-04-13
  • 打赏
  • 举报
回复
沒發現小數比較有不准的,只要同一類型數據定義同樣的精度

二進制的排列都一樣怎麼會不相等?
月影 2009-04-13
  • 打赏
  • 举报
回复
我发现这个问题不是一个简单的问题, 建议大家都去看看17楼说的那篇博客。如果能看懂, 都算是强人了。
sushou2009 2009-04-12
  • 打赏
  • 举报
回复
[Quote=引用 3 楼 sunny906 的回复:]
因为十进制小数转为二进制可能变为无限小数导致不精确
可以通过相减的差值和约定的精度相比较
例如:
if(fabs(f1-f2) <0.000001)
[/Quote]
说的不错!帮顶一个!
月影 2009-04-12
  • 打赏
  • 举报
回复
您的意思是计算机无法精确的表示0.4? 这个好像不对吧。
风龙-3 2009-04-12
  • 打赏
  • 举报
回复
应为计算机中数的表示精度有损失,在计算机中采用是二进制;浮点数的格式表达为基数、指数以及有效数;而基数为2表示的小数只能为0.5(2的-1次方),0.25 0.5+0.25等,如果要表示0.4则存在精度损失
月影 2009-04-12
  • 打赏
  • 举报
回复
请问 在C#中 2/3.0 是否等于 2 / 3.0 如下:
if (2 / 3.0 == 2 / 3.0)
{
Console.WriteLine("yes");
}
else
{
Console.WriteLine("No");
}

你认为结果是什么?(yes)
对了, 再次重申一遍, 不要说问题有没有意义或者说浮点数就是不准确, 我要的是产生这个问题的原因。
有人说, 无限循环小数表达为浮点数时会被舍入, 这个是正确的, 那么就像上面的代码一样, 两个一样的无限循环小数(他们都被舍入了)做比较。 结果会怎么样?
rczjp 2009-04-12
  • 打赏
  • 举报
回复
[Quote=引用 3 楼 sunny906 的回复:]
因为十进制小数转为二进制可能变为无限小数导致不精确
可以通过相减的差值和约定的精度相比较
例如:
if(fabs(f1-f2) <0.000001)
[/Quote]
是这样的
因为浮点数本来就不精确 两个数比较相等就不行
sillf 2009-04-12
  • 打赏
  • 举报
回复
这个很容易啊,就是在定义一个浮点类型的数的时候,本身就是一种是近似值,比如一个无限循环小数0.366666666.....,近似表示成的一个浮点数0.3667,同一个确定值的小数0.3667,在进行比较的时候,你认为能比较么?该浮点数显示出来的是0.3667,但是他的实质还是0.36666666.......,你认为比较还有意义么?
月影 2009-04-12
  • 打赏
  • 举报
回复
各位请注意, 我问的不是解决问题的办法, 而是产生问题的原因。
只有三楼的第一句话算是有效的回答。
不过还不是很精确, 如果有谁能举例说明就好了。

比如我要做如下操作:
if( 1.0/10.3 == 1.0 / 10.3)
//do something.

为什么不能这么做? 希望能用内存中的二进制的具体行为来解释这个问题产生的原因。
柳晛 2009-04-12
  • 打赏
  • 举报
回复
楼主看一下“浮点数”这个概念,理解浮点数是怎么个“浮”法,就明白为什么了。
zhu_chuan_hang 2009-04-12
  • 打赏
  • 举报
回复
浮点数一般是四舍五入后保留一定位数的数,所以不准确
十八道胡同 2009-04-12
  • 打赏
  • 举报
回复
是精度的问题吧,一般用fabs(x-y)<1e-10来判断2个浮点数相等。
zhangkunit 2009-04-12
  • 打赏
  • 举报
回复
可以如此这样实现x,y为你要比较的两个数:
fabs(x-y)<1e-9
来间接比较
zhangkunit 2009-04-12
  • 打赏
  • 举报
回复
浮点数本就是 近似值,比较没有意义
加载更多回复(3)

110,534

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧