0

我在计时器的 CALLBACK 函数中运行以下代码块。

if (start_value <= end_value) 
{
   start_value += increment_value;
}
else
{
   return 0;
}

所有三个变量都定义为 DOUBLE。

Double start_value = 26.0;
Double end_value = 28.0;
increment_value = 0.1;

在将increment_value 与start_value 相加时,变量start_value 的值并不能简单地反映相加的预期结果。比如start_value为26.0,经过一次相加,start_value的值为26.10000000001。后面的 1 会在后面的代码中引起问题,因为当比较的预期结果预期为 TRUE 时,由于后面的 1,它被评估为 false。为什么会发生这种情况?

4

1 回答 1

0

Eshan,该==运算符正在寻找精确匹配,并且应该专门用于整数比较(在可能精确的情况下)。所以,“为什么会这样?” 因为 26.10000000001 不等于 26.1。两者之间的差异有时被称为浮点误差。

只要我们使用二进制存储浮点数,就会不断出现浮点错误。这要求比较浮点数的方法必须不同于比较整数时的方法。(即对于浮点数,不能使用(x == y) ?。比较浮点数时“==”的快速而肮脏的替代方法是执行以下操作: if(abs(x-y)<epsilon ){//equal} 其中 epsilon 是一些小的容差值,例如 0.000001

所以,试试这样的东西:

int main(void)
{
    double start_value = 26.0;
    double end_value = 28.0;
    double increment_value = 0.1;

    #define EPSILON 0.000001  

    while(fabs(start_value-end_value)>EPSILON )
    {
          printf("not equal\n");
          start_value += increment_value;
    }
    printf("equal\n");
    getchar();  
}

注意: 选择 epsilon 值以匹配您将要进行的比较中有效数字的邻域。

还有许多其他的好方法,(很多人会说这不是其中之一)但我已经使用这个方法多年了,就我的目的而言,它运作良好。
这里是一个关于这个和其他方法的链接。

于 2013-10-08T16:40:04.447 回答