利点

2013-06-09 10 views
6

は私が #endifのと#elifのの#if の#ifdef #ifndefのの#else で働いたことがありません。利点

私はいくつかのソースコードを調べていたので、これらのディレクティブを幅広く使用していました。 条件付きプリプロセッサを読んだことがありますが、のような手がかりが見つからないのは、通常の条件文とどう違うかです。このオーバー

#include<iostream> 
int main() 
{ 
    int i = 0; 

    #if i == 0 
     std::cout<<"This"; 
    #else 
     std::cout<<"That"; 
    #endif 
    return 0; 
} 

また
#include<iostream> 
int main() 
{ 
    int i = 0; 

    if (i == 0) 
     std::cout<<"This"; 
    else 
     std::cout<<"That"; 
    return 0; 
} 

に使用 /ないに使用できる条件付きプリプロセッサ は、だから私は、次のコードの利点は何である不思議でしたか?

+1

まず、実行時に 'if'が評価され、コンパイル時に'#if'が評価されます。 – Aiias

+0

http://stackoverflow.com/help/dont-ask – xaxxon

+4

@ xaxxon:リンクがどのように関係しているか説明できますか? – Blender

答えて

3

条件付きプリプロセッサは、最初の例のように動作しません。

これは定数で動作していますか?コンパイル時には、さまざまな条件を調べ、それに従ってソースコードを入力/省略します。例えば

#define HAS_COMPARISON 

int main() { 
    #ifdef HAS_COMPARISON 
     int i = 0; 
     if(i == 0) std::cout << "This"; 
     else 
    #else 
     std::cout << "That"; 
    #endif 
} 

defineセットで、それは短い、それの出力は以下となりThisに...変数iを設定し、比較を実行します。その定義をコメントすると、ブロック全体がプログラム内になくなります。つまり、変数を設定したり比較したりすることなく、常にThatを出力します。

これは、プリプロセッサ定義の最も一般的な使用方法です。また、値を定義してそれらを比較して、同じ定義で可変動作を持たせることもできますが、それは別の問題です。

もう一度:条件付きプリプロセッサはコンパイル時に評価され、実行時に変数条件が評価されます。

+0

〜私が間違っていれば訂正してください。** HAS_COMPARISON **を0に設定するとコンパイラは_deadコードの消去と同様に_ _ else_&_#endif_ブロックを削除します。 – ikis

+0

@iKishore *プリプロセッサ*は、コンパイラが認識する前にコードを削除します。条件付きのコードは、コンパイラが見たときにエラーを引き起こす可能性があります(タイプエラーや機能不足など)。 – delnan

+1

@iKishoreいいえ、あなたは正しいです。 ANY値に設定すると '#else'が削除され、' #define'がコードから削除されると、 '#ifdef'から'#else'までの全てが削除されます。 –

1

条件付きコンパイルとは、最終的にリンクされたアプリケーションに定義されたコードが実際には存在しないことを意味します。言語条件を使用するだけで、両方のブランチが最終コードに含まれていることを意味し、テストするのがより困難になる可能性があります。

コンパイル時に何が必要なのかを知っているときは、#ifdefなどを使用します。言語条件は、実行時まで必要なものがわからないときに使用されます。

1

プリプロセッサの利点は、コードが投げ捨てられることです。それはコンパイルされず(時間がかかります)、ラムにロードされるマシンコードは生成されません。決定が非常にタイトなループで大量に実行されている場合は、スピードが向上する可能性があります。あなたが実際に時間を計らなければ、これが重要であるとは思わないでください。

プリプロセッサの障害は、明らかにコンパイル時に答えを知る必要があることです。ソースコードには今まで実行されなかった多くのコードが含まれています。コンパイル時の値がどのようなものであったのかを判断することは困難な場合が多いため、人間にとっては辿るのが難しくなります。

+0

実際に、条件がコンパイル時定数であり、プリプロセッサがオプションであるとすれば、コンパイラは通常、そのことを推測して、 ifと一緒に。 – delnan

+0

真実。スマートコンパイラのしくみを覚えておくと良いでしょう。人々はしばしば早すぎる最適化を試みるために混乱しているコードを書いて、それが速くならなかったことを認識し、読み込み/保守がより困難になります。 – xaxxon

4

あなたが示した例は、他の情報がないため役に立たないようです。しかしここには#ifが有用であるという例があります。

#if OS == LINUX 
//do something 
#elif OS == SOLARIS 
//do something else 
#else 
// 
#endif 

キーは#ifはコンパイル時に評価されていることですが、プログラムの実行時にifが評価されます。

#if BYTE_ORDER == LITTLE_ENDIAN 
//do something 
#else 
//do something else 
#endif 
2

この場合、プリプロセッサディレクティブの使用は完全には有用ではありません。しかし、これらのプリプロセッサ・ディレクティブの使用は、他の多くの場合に有用です。

これらのプリプロセッサディレクティブは、条件付きコンパイルに使用できます。例えばいくつかのプログラムを複数のプラットフォーム用に開発する必要がある場合、プラットフォーム固有の定数に値を与えることができます。これらの値を変更することは、コード全体を1つの大きなエンティティとして維持しながら、プラットフォーム固有のコンパイルを行うことができます。

これらはデバッグ中にも便利です。テストユニットは、コードにコンパイルし、デバッグ中にこれらの条件付きコンパイルを使用して実行することができ、これらを使用してコンパイルから停止することができます。