gpt4 book ai didi

c++ - 关于C++中的 float 比较

转载 作者:行者123 更新时间:2023-11-28 00:40:25 27 4
gpt4 key购买 nike

我有一个循环在给定的最小和最大范围之间循环一个 float ,如下所示

#include <iostream>
using namespace std;

void main(void)
{
for (double x=0.012; x<=0.013; x+=0.001)
{
cout << x << endl;
}
}

这是非常简单的代码,但据我所知,在计算机语言中,我们需要比较两个 float 并考虑 EPS。因此,上面的代码不起作用(我们希望它从 0.012 到 0.013 循环两次,但它只循环一次)。所以我手动给上限加上一个EPS。

#include <iostream>
using namespace std;
#define EPS 0.0000001

void main(void)
{
for (double x=0.012; x<=0.013+EPS; x+=0.001)
{
cout << x << endl;
}
}

现在可以使用了。但手动执行此操作看起来很丑陋,因为 EPS 应该真正取决于机器。我正在将我的代码从 matlab 移植到 C++,我在 matlab 中没有问题,因为有 eps 命令。但是在 C/C++ 中有类似的东西吗?

最佳答案

捏造比较是错误的使用方法。即使您的比较“正确”,浮点循环计数器也会在迭代之间累积误差。

您可以通过对循环计数器使用精确算法来消除错误的累积。它可能仍然是浮点类型,但您使用的是完全可表示的值,例如:

for (double i = 12; i <= 13; ++i)

然后,在循环内,您可以根据需要缩放计数器:

for (double i = 12; i <= 13; ++i)
{
double x = i / 1000.;

}

显然,在具有两次迭代的循环中累积的误差并不多。但是,我希望你的值(value)观只是一个例子,在实践中可能会有更长的循环。使用这种技术,x 中的唯一错误是在缩放操作中,因此每次迭代中只有一个错误,而不是每次迭代中有一个错误。

请注意,除以 1000 比缩放 0.001 更准确。除以 1000 只有一个错误(在除法中)。但是,由于 .001 不能用二进制 float 精确表示,因此乘以它有两个错误(将 .001 转换为 float 和乘法)。另一方面,除法通常是一个非常慢的操作,因此您可以选择乘法。

最后,尽管此技术保证了所需的迭代次数,但由于缩放中的舍入误差,缩放值可能会在第一次或最后一次迭代中略微超出理想目标间隔。如果这对您的应用程序很重要,您必须在这些迭代中调整值。

关于c++ - 关于C++中的 float 比较,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19204938/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com