なぜ代わりにstd::runtime_error::what()戻るのですか?多くの場合、埋め込まれた文字列への参照を直接返すと便利であり、オーバーヘッドを回避できます。では、そもそも内部文字列へのconst参照を返さず、オーバーロードされた関数を提供しない理由は何でしょうか。文字列コンストラクタが例外をスローできることにも対応していると思いますが、文字列参照を返すリスクはありません。const char*std::string const&
3 に答える
std::runtime_errorstd::exceptionはwhich定義から継承するvirtual const char* what() const throw();ため、最も単純な応答は、関数のオーバーロードであり、標準の例外がそのように定義していることを確認できます。(実装によっては)を返すことは可能かもしれませstd::stringんが、他の標準ライブラリとは矛盾します。
what()返される理由は、const char*失敗する可能性のある(特に例外をスローする可能性のある)操作を回避できるためだと思います。失敗してはならない次のコードを検討してください
virtual const char* what() const throw() {
return "An error has occured";
}
ただし、次のコードでは、の割り当てstd::stringが失敗し、例外がスローされる可能性があります。
std::string what() const throw() {
return std::string("An error has occured");
}
文字列のコンストラクターがここにスローされた場合、関数がを指定しているため、アプリケーションは何があってもクラッシュする可能性がありますthrow()。
例外内で使用std::stringすると、メモリを割り当てる必要が生じますが、これは不可能な場合があります(std::bad_allocからも継承することに注意してくださいstd::exception)。
必ずしも埋め込まれているわけではありませんstd::string。whatメンバー関数は仮想です。つまり、オーバーライドされるように設計されています。それをオーバーライドする主な理由は、によって使用されるメカニズムを介する以外の方法で文字列を提供することですstd::runtime_error(そのメカニズムが何であれ、おそらく格納されていますstd::string)。
runtime_errorはパラメータとしてstd::stringを受け取るので、それを保持して、提案どおりに返すことができますが、what()メソッドはstd :: exceptionから継承されるため、より一般的です。
例外をスローするオーバーヘッドは、スタックが巻き戻されることですでに高くなる可能性が高いため、この少し余分なオーバーヘッドについて心配する必要はありません。