1. ホーム
  2. c++

[解決済み] float a = 3.0;' は正しい文か?

2023-04-30 17:34:37

質問

以下のような宣言があった場合。

float a = 3.0 ;

はエラーになるのか?ある本で読んだのですが 3.0double の値として指定しなければならないこと。 float a = 3.0f . そうなのでしょうか?

どのように解決するのですか?

を宣言することはエラーではありません。 float a = 3.0 と宣言してもエラーにはなりませんが、そうするとコンパイラが3.0のダブルリテラルをフロートに変換してしまいます。


しかし、あなたは でなければなりません。 は特定のシナリオでfloatリテラル表記を使用します。

  1. パフォーマンスのため。

    具体的には、以下のように考えてください。

    float foo(float x) { return x * 0.42; }
    
    

    ここで、コンパイラはそれぞれの戻り値に対して(実行時に支払うことになる)変換を出力します。それを避けるために、宣言する必要があります。

    float foo(float x) { return x * 0.42f; } // OK, no conversion required
    
    
  2. 結果比較時のバグを回避するため。

    例えば、次の比較は失敗します。

    float x = 4.2;
    if (x == 4.2)
       std::cout << "oops"; // Not executed!
    
    

    float リテラル記法で修正できます.

    if (x == 4.2f)
       std::cout << "ok !"; // Executed!
    
    

    (注)もちろん は浮動小数点数または倍数を等しく比較する方法ではありません。 )

  3. 正しいオーバーロードされた関数を呼び出すため(同じ理由で)。

    void foo(float f) { std::cout << "\nfloat"; }
    
    void foo(double d) { std::cout << "\ndouble"; }
    
    int main()
    {       
        foo(42.0);   // calls double overload
        foo(42.0f);  // calls float overload
        return 0;
    }
    
    
  4. サイバーが指摘するように を推論するのを助けることが必要です。 float :

    の場合 auto :

    auto d = 3;      // int
    auto e = 3.0;    // double
    auto f = 3.0f;   // float
    
    

    また、同様に、テンプレート型控除の場合 :

    void foo(float f) { std::cout << "\nfloat"; }
    
    void foo(double d) { std::cout << "\ndouble"; }
    
    template<typename T>
    void bar(T t)
    {
          foo(t);
    }
    
    int main()
    {   
        bar(42.0);   // Deduce double
        bar(42.0f);  // Deduce float
    
        return 0;
    }
    
    

ライブデモ