web-dev-qa-db-ja.com

strlenがNULLをチェックしない

strlen()がNULLをチェックしないのはなぜですか?

strlen(NULL)を実行すると、プログラムセグメンテーションエラーが発生します。

その背後にある根拠を理解しようとする(もしあれば)。

26
hari

その背後にある合理性は単純です-存在しないものの長さをどのように確認できますか?

また、「管理言語」とは異なり、ランタイムシステムが無効なデータまたはデータ構造を正しく処理することは期待されていません。 (このタイプの問題は、アプリケーションを必要とする非計算またはパフォーマンスの低い方により多くの「現代」言語がより人気がある理由です。).

Cの標準テンプレートは次のようになります

 int someStrLen;

 if (someStr != NULL)  // or if (someStr)
    someStrLen = strlen(someStr);
 else
 {
    // handle error.
 }
31
Hogan

言語の一部 標準 文字列処理ライブラリを定義する部分は、特定の関数に対して特に指定されない限り、すべてのポインター引数must有効な値があります。

C標準ライブラリの設計の背後にある哲学は、プログラマーが実行時チェックを本当に実行する必要があるかどうかを最終的に知るのに最適な立場にいるということです。総システムメモリがキロバイト単位で測定されていた時代に戻って、不要なランタイムチェックを実行するオーバーヘッドはかなり痛いものでした。そのため、C標準ライブラリはこれらのチェックを実行しません。本当に必要な場合は、プログラマーが既にそれを行っていると想定しています。あなたがknowなら、strlenに悪いポインタ値を決して渡さないでしょう(例えば、文字列リテラルを渡している、またはローカルに割り当てられた配列)、NULLに対するunnecessaryチェックで結果のバイナリを乱雑にする必要はありません。

19
John Bode

あなたの悲しみを助ける小さなマクロ:

#define strlens(s) (s==NULL?0:strlen(s))
5
Stoian Ivanov

標準はそれを必要としないため、実装はテストを回避し、潜在的に高価なジャンプを回避します。

5
ninjalj
size_t strlen ( const char * str );

http://www.cplusplus.com/reference/clibrary/cstring/strlen/

Strlenは文字配列へのポインタをパラメータとして受け取ります。nullはこの関数の有効な引数ではありません。

3
Casey Flynn

3つの重要な理由:

  • 標準ライブラリとC言語は、プログラマが何をしているのかを知っていることを前提に設計されているため、nullポインタはEdgeケースとしてではなく、未定義の動作をもたらすプログラマの間違いとして扱われます。

  • 実行時のオーバーヘッドが発生します-strlenを数千回呼び出し、常にstr != NULLはプログラマーが弱虫として扱われない限り合理的ではありません。

  • 合計するとコードサイズが大きくなります-ほんの数命令で済みますが、この原則を採用してどこでも実行すると、コードが大幅に膨張する可能性があります。

2