zoukankan      html  css  js  c++  java
  • 危险的浮点数float

    今天写程序又以为我见鬼了!最后查出来发现原来又是浮点数搞的鬼!

    情况大致是这样的,我想要测试向量运算的速度,所以要对一个浮点数向量进行求和运算,代码如下:

    int vect_size=100000000;
    vector<float> vect1(vect_size,0.1);
    float sum=0;
    for(int i=0;i<vect1.size();++i){
    	sum+=vect1[i];
    }
    printf("%f
    ",sum);
    

    10^8个0.1求和,地球人都知道结果应该是10^7,运行结果竟然是……2.097152*10^7

    我了个擦!我读书少你也不能这么骗我啊!

    当vect_size为10000时,运行结果为999.902893,说明错误是累加形成的,并非溢出之类的造成的。

    注意我保留了小数点后这么多位,原因是在不同的电脑上运行,结果是相同的,即都会产生这么大的偏差。

    如果我把float换成double,那么结果是没有问题的。

    我猜想了一下原因:

    float的精度有一定的上限,对于任何小数,float都只能是用一个最接近的数来表示,并不是完全一样的数,即float是不连续的。所以0.1在float中是不存在的,只存在0.100000001(举个例子~),而这个规则是float的定义造成的,并非编译器或运行环境决定的,所以在不同的电脑上运行结果相同。此外,double的精度更高,所以在1亿这个量级上还看不出误差。

    是否真是这样,等有时间研究下float再说。

    不过这么看,float真是蛮危险的,因为其反直觉,所以很有可能给程序造成一些意料之外的结果(就是我说的见鬼了)。

    我上一次见鬼也是跟float有关,大致代码如下:

    float f=0.1;
    if(f==0.1){
       printf("equal!");   
    }
    

    当时还是用python写的,死活不通过……其实原因上面已经提到了。

    float当真反直觉!代码中的不确定因素!

  • 相关阅读:
    csu1217: 奇数个的那个数
    小试SAS 判别分析
    bfs poj2965
    STL set常用操作
    csu1002 A+B(III)
    HDOJ 1002 的几种方法
    SQL知识积累
    CSV文件格式介绍
    ASP.net Web Form 知识积累
    C# 位域[flags] 枚举
  • 原文地址:https://www.cnblogs.com/plwang1990/p/4146959.html
Copyright © 2011-2022 走看看