为什么float的相同值和使用函数atof转换为float的字符串不相等?

时间:2012-08-05 07:01:36

标签: c

我在C中编写了一个程序,当我比较浮点数和使用函数atof转换为float的字符串的相同值时,结果为NOT EQUAL。

    #include<stdio.h>

    main(){

            char str[10] = "54.23" ;
            float val = 54.23 ;


            if( atof(str) == val )
                 printf("\nconverted correctly");
            else
                 printf("\nThen What is the use of atof\n ");


       }

本程序显示输出:“那么atof的用途是什么” 请告诉我为什么这个程序会显示这种匿名行为?

4 个答案:

答案 0 :(得分:5)

永远不要使用==

测试浮点数/双精度数是否相等

以下是您的代码版本,它实际显示了相关的值:

#include <stdio.h>
#include <stdlib.h>

int main()
{
    char str[10] = "54.23";
    float val = 54.23;

    printf("atof(str) = %.15f\n", atof(str));
    printf("      val = %.15f\n", val);

    return 0;
}

当你运行它时,你会看到:

$ gcc -Wall atof.c
$ ./a.out 
atof(str) = 54.229999999999997
      val = 54.229999542236328
$

值接近,在单个精度浮点数的预期精度范围内,但它们不相同。此外,正如其他人所指出的那样,atof会返回double,因此您要将float提升为double的值与全精度double进行比较由atof返回。

与此类问题一样,在使用代码中的浮点运算进一步处理之前,请先阅读this。 “带回家的消息”是你永远不应该将浮点数或双打数与==进行比较 - 总是将绝对差值与适当的容差值进行比较。

答案 1 :(得分:2)

因为val是一个int;当你指定它54.23时,它将被截断为54.而54!= 54.23。

即使它是浮动的,你也不能指望它们是平等的。 Here's why.

答案 2 :(得分:1)

double atof(char *str);\\it return double not a float

这种比较是在float和double之间。当你在两种不同类型之间进行比较时,你可能会得到一些意想不到的输出。因为每种数据类型都有不同的内存表示以及不同的访问机制。

float以不同的形式表示在内存中,与double相比。

您可以在维基百科中了解更多相关信息

http://en.wikipedia.org/wiki/Floating_point#Internal_representation

您应该再次包含头文件

#include <stdlib.h> \\prototype of atof() present in this header.

如果在使用该功能之前未提供正确的原型,那么

默认情况下返回函数类型int。所以我认为返回结果肯定与您预期的不同。

答案 3 :(得分:0)

您几乎从不想要检查与浮点数的相等性,因为teensy差异将被视为不相等。还有其他问题。例如,即使您使用双精度,例如,十进制数“0.1”也表示为“0.10000000000000001”。

在这种情况下,您的“val”变量是双精度文字,它被强制转换为浮点数。结果可能不完全准确。其次,您的字符串文字需要从基数10转换为基数2倍。因此,为了将atof值与您的文字进行比较,atof将基数为10的字符串转换为基数为2的两倍,而“val”则从基数为10的字面值转换为基数为2的两倍为基数为2的浮点数,然后为向后转发到一个基数为2的双倍进行比较。

事实上,我不打算将完全确定为精确丢失的地方。如保罗的代码可能建议并将值与容差中的值进行比较。