- ベストアンサー
(void)0 はどんな意味ですか
assert.h を見ると、次のように書かれています。 #define assert(x) ((void)0) 文法的に (void)0 どのように解釈出来るのでしょう。 次のプログラムで試すとエラーにもならず、コンパイラ結果を見ると何もしていないのが分かりました。 void main(void) { (void)0 ; }
- みんなの回答 (3)
- 専門家の回答
質問者が選んだベストアンサー
> 文法的に (void)0 どのように解釈出来るのでしょう。 文法的には,単純に,0をvoid型にキャストしているだけです。 cast-expression: (void)0 as '(' type-name ')' cast-expression type-name: void cast-expression: 0 as unary-expression unary-expression: 0 as postfix-expression postfix-expression: 0 as primary-expression primary-expression: 0 as constant そして,void型への型変換は,規格 (ISO/IEC 9899:1999) の 6. Language - 6.3 Conversions - 6.3.2 Other operands - 6.3.2.2 void に説明があり, > If an expression of any other type is evaluated as a void expression, its value or designator is discarded. と書かれています。 つまり,値0は単純に破棄されます。 ちなみに,全ての式文は,6.8.3 Expression and null statementの第2段落に > The expression in an expression statement is evaluated as a void expression for its side effects. とあるため,voidへのキャストがあるかのように扱われます。
その他の回答 (2)
- mtaka2
- ベストアンサー率73% (867/1179)
C言語では、関数呼び出しも代入計算も、基本的に全ての文は「式」に「;」を付けたものになっています。 「func();」という文は、「func()」という式を文にしたものになります。 「b=a+1;」という文は、「b=a+1」という式を文にしたものになります。 同じように、「0;」という文は、「0」という式を文にしたものになります。 ただし、このままだと数式の値を何にも利用していませんから、 コンパイラはバグの可能性を考えて「式の結果を利用していない」という警告を出す場合があります。(例えば、「a+1;」も文としては正しいですが、何の意味もない式文ですので、記述者が間違えている可能性が高いと推測できます) そこで、「0」という式をvoidにキャストする「(void)0」にすると、式の値を使っていないことを明示できるため、そういう警告を出さないようにできるのです。 では、非デバッグ時にassertの定義がなぜこのような形になっているかというと、 if (foo) assert(bar); といった形でassertが使われた時に、assert の効果は無くしつつも、assertを式として成立させて、if文としての体裁は変わらないようにしているのです。
お礼
早速の回答有り難う御座います。 mtaka2さんの回答を見て下記のプログラムで試した所、コンパイラからは警告もエラーも有りませんでした。 ルネサスのマイコン用コンパイラHEWを使っています。 MISRA C と言うC言語のチェッカでは次の警告が有りました。 0 ; 何の副作用も無いという警告有り 1 == 1 ; 何の副作用も無いという警告有り (void)0 ; 何の副作用も無いという警告有り if (1) ; {}を付けた方が良いと言う警告有り if (1){} ; 警告無し if (1){(void)0;}; 何の副作用も無いという警告有り (void)0 を使えば警告は出なくなる事を期待したのですが、出るようです。
- Tacosan
- ベストアンサー率23% (3656/15482)
「void へのキャスト」は「評価した値を使わない」ことを明示することになります. 「関数呼び出しや副作用を一切持たない式文にたいして警告を出す」処理系においては, 「void にキャストする」ことでそのような警告を抑制することができます.
お礼
いつも回答有り難う御座います。 void と同じように無い事を明確にする訳ですね。 int から long にキャストする例は見かけますが、void にキャストしたらエラーかポインタような感じがしますよね。
お礼
回答有り難う御座います。 詳しいですね。規格を此処まで熟知している人は少ないと思います。 頼りになります。 英語の勉強にもなりました。 また質問したときには、宜しくお願いします。