2017-07-28 9 views
8

は、次のコードを考えてみましょう:constexpr関数でC文字列を返す:なぜコンパイラから警告が出ないのですか?

constexpr auto f() 
{ 
    auto str = "Hello World!"; 
    return str; 
} 

int main(int argc, char* argv[]) 
{ 
    static constexpr auto str = f(); 
    std::cout << str << std::endl; 
    return 0; 
} 

は私のコンパイラが警告を通常表示されないことということですか?定義された動作ですか?プログラムに"Hello World!"と表示されるという保証はありますか?私は"Hello World!"がその機能の範囲を超えて生きていないと期待しています...

答えて

13

C++ string literalsには、プログラムが実行されている限り生きています。したがって、fから返された文字列リテラルへのポインタは常に有効です。割り当てや割り当て解除は必要ありません。

文字列リテラルのタイプはconst char[N]であり、に減ってautoタイプの減算が行われることに注意してください。あなたの目的はstd::stringを使用していた場合は、直接

auto str = std::string("Hello World!"); 

またはoperator""sを使用し、それを構築することができます。

using std::string_literals; 
auto str = "Hello World!"s; 

std::stringがリテラルタイプではないので、これはもうcannot be constexpr値。

+1

"文字列リテラルには、' const char * '型があります。 –

+0

@ T.C。 'const char'コンクリートの長さの配列? – Orient

+0

@ T.C。本当に、ありがとう。 – lisyarus

5

これはの第2の効果のautoです。あなたが考えることは、コンパイラが決めるものではないということです。これは間違ったプログラマーの期待につながります。規則はここにありますコンパイラは常にを獲得します。

ここでの事実は、strが(静的記憶期間)文字列litteralに対してconst char *であるということです。それはビルド時に完全に決定できるので、有効なconstexprです。

関連する問題