C++ 中的 while 循环中的浮点错误

Floating point error in while loop in C++

本文关键字:错误 中的 while 循环 C++      更新时间:2023-10-16
int main()
 {
      float x = k ; // k is some fixed positive value 
      while(x>0)
           x-- ;
      return 0 ;
 }

上面的程序可以无限循环吗?

是的,这是可能的。以最大浮点数为例。

如以下代码所示,对于最大的浮点数mm等于m - 1

#include <iostream>
#include <limits>
int main() {
    auto m = std::numeric_limits<float>::max();
    auto l = m;
    l--;
    std::cerr << (m == l) << "n";
}

演示:http://ideone.com/Wr9zdN

因此,使用此起始值,循环将是无限的。

为什么?

float(与其他所有内置类型一样)具有有限的精度。要使x - 1可以用x以外的数字表示,小于x的最大数之间的差必须小于2。

现在让我们计算m,最大浮点数和x之间的差值,最大浮点数,严格小于m

#include <iostream>
#include <cmath>
#include <limits>
int main() {
    auto m = std::numeric_limits<float>::max();
    std::cout << "float max: " << m << "n";
    auto x = std::nextafter(m, 0.0f);
    std::cout << "biggest value less than max: " << x << "n";
    auto d = m - x;
    std::cout << "the difference: " << d << "n";
}

演示:http://ideone.com/VyNgtE

事实证明,这两个数字之间存在巨大的2.02824e+31差距。远远大于 1。1 实在是太小了,无法发挥作用。

是的,可以。例如,如果k FLT_MAX。没有足够的精度来处理如此大的数字之间的如此小的距离。

#include <float.h>
#include <stdio.h>
int main()
{
    float a = FLT_MAX;
    float b = a - 1;
    printf("%.10fn", a - b);
    return 0;
}

输出:

0.0000000000
我认为实际上

可以。如果k足够大,四舍五入将吞噬您的递减。