2

C でプログラムを作成しましたが、float の同じ値と、関数 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

4 に答える 4

5

float/double が等しいかどうかをテストしない==

問題の値を実際に表示するコードのバージョンを次に示します。

#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
$

値は、単精度浮動小数点数の予想される精度の範囲内で近似していますが、同一ではありません。また、他の人が指摘したように、atofa を返すため、 aに昇格された aの値を、によって返される完全な精度doubleで比較しています。floatdoubledoubleatof

このタイプの質問と同様に、コードで浮動小数点演算をさらに進める前に、これを読んでください。「持ち帰りのメッセージ」は、float や double を決して比較してはならないということです==。絶対差を常に適切な許容値と比較してください。

于 2012-08-05T07:28:05.210 に答える
2

valは int であるためです。割り当てると54.23、54 に切り捨てられます。また、54 != 54.23 になります。

たとえそれがフロートだったとしても、それらが等しいとは期待できませんでした。理由は次のとおりです。

于 2012-08-05T07:04:56.910 に答える
0

わずかな違いは不等として読み取られるため、浮動小数点数で等値をチェックすることはほとんどありません。他にも問題があります。たとえば、倍精度を使用しても、たとえば 10 進数の「0.1」は「0.10000000000000001」と表現されます。

この場合、「val」変数は倍精度リテラルであり、float にキャストされます。結果はおそらく完全に正確ではありません。次に、文字列リテラルを基数 10 から基数 2 の double に変換する必要があります。したがって、atof 値をリテラルと比較するために、atof は基数 10 の文字列を基数 2 の double に変換しますが、「val」は基数 10 のリテラルから基数 2 の double、基数 2 の float に変換され、アップキャストされて に戻されます。比較を行う基数 2 倍精度。

実際のところ、失われた精度がどこに行ったのかを正確に特定するつもりはありません。ポールのコードが示唆するように行い、値を許容範囲内で比較します。

于 2012-08-05T07:30:33.300 に答える