web-dev-qa-db-ja.com

#if 0 ..... #endifブロックは正確に何をしますか?

In C/C++

#if 0/#endifブロックの間に配置されたコードはどうなりますか?

#if 0

//Code goes here

#endif

コードは単にスキップされるため、実行されませんか?

115
vette982

実行されないだけでなく、コンパイルもされません。

#ifはプリプロセッサコマンドであり、実際のコンパイル手順の前に評価されます。そのブロック内のコードは、コンパイルされたバイナリには表示されません。

多くの場合、後で再び有効にするために一時的にコードのセグメントを削除するために使用されます。

132
David

1つの重要な違いを除いて、ブロックをコメントアウトするのと同じです。ネストは問題ではありません。次のコードを検討してください。

foo();
bar(x, y); /* x must not be NULL */
baz();

コメントアウトしたい場合は、次のことを試してください。

/*
foo();
bar(x, y); /* x must not be NULL */
baz();
*/

Bzzt。構文エラー!どうして?ブロックコメントはネストされないため(SOの構文の強調表示からわかるように)、単語 "NULL"の後に*/がコメントを終了し、baz呼び出しはコメントアウトされず、*/bazの後に構文エラー。一方:

#if 0
foo();
bar(x, y); /* x must not be NULL */
baz();
#endif

全体をコメントアウトするように機能します。そして、#if 0sは次のように互いにネストします:

#if 0
pre_foo();
#if 0
foo();
bar(x, y); /* x must not be NULL */
baz();
#endif
quux();
#endif

もちろん、これは少し混乱する可能性があり、適切にコメントしないとメンテナンスの頭痛になります。

66
Tyler McHenry

コンパイラがそれをコンパイルしないように、そのコードを永久にコメントアウトします。

コーダーは、後で#ifdefを変更して、必要に応じてそのコードをプログラムでコンパイルできます。

コードが存在しないのとまったく同じです。

17
Nilbert

#elseケースに追加したい:

#if 0
   /* Code here will NOT be complied. */
#else
   /* Code will be compiled. */
#endif


#if 1
   /* Code will be complied. */
#else
   /* Code will NOT be compiled. */
#endif
12
Steven Xu

#if 0…#endifブロックは正確に何をしますか?

著者がバージョン管理システムについて聞いたことがないことは明らかです。これにより、可能な限り遠くに走るように指示されます…

12
Jörg W Mittag

プリプロセッサが#ifを確認すると、次のトークンにゼロ以外の値があるかどうかを確認します。存在する場合、コンパイラーのためにコードを保持します。そうでない場合は、そのコードを削除するため、コンパイラはそれを認識しません。

誰かが#if 0と言った場合、彼らは効果的にコードをコメントアウトしているので、コンパイルされません。これは、周囲に/ * ... * /を置いた場合と同じと考えることができます。まったく同じではありませんが、同じ効果があります。

何が起こったのかを詳細に理解したい場合は、よく見ることができます。多くのコンパイラでは、プリプロセッサの実行後にファイルを表示できます。たとえば、Visual C++では、switch/Pコマンドはプリプロセッサを実行し、結果を.iファイルに入れます。

6
Steve Rowe

#で始まる行は プリプロセッサディレクティブ です。 #if 0 [...] #endifブロックはコンパイラに到達せず、マシンコードを生成しません。

ソースファイルifdef.cxxを使用して、プリプロセッサで何が起こるかを示すことができます。

#if 0
This code will not be compiled
#else
int i = 0;
#endif

gcc -E ifdef.cxxを実行すると、コンパイルされる内容が表示されます。

このメカニズムを使用して、開発サイクル中にコードのブロックがコンパイルされないようにすることもできますが、ソース管理にチェックインしたくない場合があります。コメントアウトされている歴史的なコードの場合は、削除する必要があります。ソース管理には履歴が含まれていますよね?

また、答えはCC++の両方で同じかもしれませんが、C/C++と呼ばれる言語はなく、そのような言語を参照するのは良い習慣ではありません。

3
Johnsyweb

まったくない

int main(void)
{
   #if 0
     the apostrophe ' causes a warning
   #endif
   return 0;
}

Gcc 4.2.4で「t.c:4:19:警告:終了 '文字がありません」と表示されます

1

これはコメントアウトする安価な方法ですが、デバッグの可能性があると思われます。たとえば、ファイルに値を出力するビルドがあるとします。 #if 0 ... #endifを使用できるように、最終バージョンではそれを望まないかもしれません。

また、デバッグ目的でそれを行うより良い方法は次のようになると思います:

#ifdef DEBUG
// output to file
#endif

あなたはそのようなことをすることができ、それはより理にかなっているかもしれません、そしてあなたがしなければならないのは結果を見るためにDEBUGを定義することです。

0
Daniel