このマクロが10ではなく20に置き換えられるのはなぜですか?

OneZero:
1. #define NUM 10
2. #define FOO NUM
3. #undef NUM
4. #define NUM 20
5. 
6. FOO

プリプロセッサのみを実行すると、出力ファイルには20が含まれます。

ただし、私が理解していることから、プリプロセッサは単にテキストの置換を行います。だからこれは私が起こっていると私が思うことです(これは明らかに間違っていますがばかげています):

  1. NUMは10と定義されています。
  2. したがって、2行目でNUMは10に置き換えられています。したがって、「#define FOO 10」が作成されています。
  3. NUMは未定義です。
  4. NUMが再定義され、現在は20です。
  5. FOOは、4行目の再定義の前の10行目である2行目に従って置き換えられます。

だから私は出力が20ではなく10であるべきだと思います。それがどこでうまくいかなかったのか何か説明できますか?

いう:

標準から関連するすべての仕様を収集するために、コメントスレッドからこの情報を抽出し、ドラフトN4527に基づいてC ++セクション番号を追加しました(2つの標準で規範的なテキストは同じです)。基準は、主題に関して完全に明確です。

  1. #define プリプロセッサディレクティブはマクロの置換を受けません。

    (C11§6.10¶7; C ++§16[cpp]¶6):前処理ディレクティブ内の前処理トークンは、特に明記されていない限り、マクロ展開の対象にはなりません。

  2. マクロが置換テキストで置き換えられた後、新しいテキストが再スキャンされます。プログラムのその時点でトークンのアクティブなマクロ定義がある場合、置換内のプリプロセッサトークンはマクロとして展開されます。

    (C11§6.10.3¶9; C ++§16.3[cpp.replace]¶9)次の形式の前処理ディレクティブ

    # define identifier replacement-list new-line

    マクロ名の後続の各インスタンスを、ディレクティブの残りの部分を構成する前処理トークンの置換リストで置き換えるオブジェクトのようなマクロ定義します次に、以下に指定されているように、置換リストを再スキャンして、より多くのマクロ名を探します。

  3. マクロ定義は、マクロ名のforの後の行から、またはファイルの終わり#defineまでアクティブ#undefです。

    (C11§6.10.3.5¶1; C ++§16.3.5[cpp.scope]¶1)マクロ定義は、対応する#undefディレクティブが検出されるまで、または(検出されない場合は)、前処理翻訳単位。マクロ定義は、翻訳フェーズ4以降は意味がありません。

プログラムを見ると:

#define NUM 10
#define FOO NUM
#undef NUM
#define NUM 20
FOO 

NUM1行目のマクロ定義は3行目まで続くことがわかります。これらの行には置換可能なテキストがないため、定義は使用されません。したがって、プログラムは事実上次のものと同じです。

#define FOO NUM
#define NUM 20
FOO 

このプログラムでは、第三のラインで、存在のためにアクティブな定義でFOO置換リストと、NUM、およびのためのNUM置換リストと、20FOOそれを作る、その置換リストに置き換えられNUM、次いでそれは再び、その結果、マクロスキャンされNUM、最終結果は、ということであるので、交換が再び再スキャンされることをその置換リスト20で置換され、ない定義されたマクロがありますトークン20は変換フェーズ5での処理に残されます。

この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。

侵害の場合は、連絡してください[email protected]

編集
0

コメントを追加

0

関連記事

分類Dev

配列値が追加されるのではなく置き換えられるのはなぜですか?

分類Dev

要素が追加されるのではなく置き換えられるのはなぜですか?

分類Dev

`!45`が` top`に置き換えられるのはなぜですか?

分類Dev

@が_at_に置き換えられたのはなぜですか?(CoffeeScript)

分類Dev

この例では、関数名を戻り値に置き換えられないのはなぜですか?

分類Dev

変数で値が置き換えられないのはなぜですか?

分類Dev

あるプロジェクトの依存関係が既存の依存関係に置き換えられるのはなぜですか

分類Dev

配列の最後の要素が0に置き換えられるのはなぜですか

分類Dev

Retrofit @Pathが置き換えられないのはなぜですか?

分類Dev

AppleScriptで「ターミナル」が「アプレット」に置き換えられるのはなぜですか?

分類Dev

IPv6でARPがNDPに置き換えられるのはなぜですか?

分類Dev

この関数をラムダに置き換えられないのはなぜですか

分類Dev

なぜこのhaskellの行では、$を置き換えることができないのですか()

分類Dev

このsedコマンドが行に追加される代わりに行を置き換えるのはなぜですか?

分類Dev

「g」を追加して文字列をsedに置き換えることができるのはなぜですか?

分類Dev

なぜ✓記号が「1」に置き換えられることがあるのですか?

分類Dev

これらの関数でzshがハイフンをアンダースコアに置き換えるのはなぜですか?

分類Dev

htaccessが正しく書き換えられないのはなぜですか

分類Dev

envsubstが/を置き換えるのはなぜですか

分類Dev

マージされたデータフレームの値を置き換えることができないのはなぜですか?

分類Dev

このような文字列のcharを置き換えられないのはなぜですか?

分類Dev

特定の文字列で\ nを置き換えることができないのはなぜですか?

分類Dev

Replaceメソッドを使用すると文字列が置き換えられないのはなぜですか?

分類Dev

シェルでmysqlコマンドを文字列に置き換えることができないのはなぜですか?

分類Dev

コマンド展開に埋め込まれた改行が空白に置き換えられるのはなぜですか?

分類Dev

Automatorで、ファイルパスのスラッシュがコロンに置き換えられるのはなぜですか?

分類Dev

Kotlinの文字列リソースファイルからの文字列であるのに、文字列が置き換えられないのはなぜですか?

分類Dev

[表示]をクリックすると、常に最初のデータが置き換えられるのはなぜですか?

分類Dev

スクロールのロゴを置き換えるこのjQueryスクリプトが機能しないのはなぜですか?

Related 関連記事

  1. 1

    配列値が追加されるのではなく置き換えられるのはなぜですか?

  2. 2

    要素が追加されるのではなく置き換えられるのはなぜですか?

  3. 3

    `!45`が` top`に置き換えられるのはなぜですか?

  4. 4

    @が_at_に置き換えられたのはなぜですか?(CoffeeScript)

  5. 5

    この例では、関数名を戻り値に置き換えられないのはなぜですか?

  6. 6

    変数で値が置き換えられないのはなぜですか?

  7. 7

    あるプロジェクトの依存関係が既存の依存関係に置き換えられるのはなぜですか

  8. 8

    配列の最後の要素が0に置き換えられるのはなぜですか

  9. 9

    Retrofit @Pathが置き換えられないのはなぜですか?

  10. 10

    AppleScriptで「ターミナル」が「アプレット」に置き換えられるのはなぜですか?

  11. 11

    IPv6でARPがNDPに置き換えられるのはなぜですか?

  12. 12

    この関数をラムダに置き換えられないのはなぜですか

  13. 13

    なぜこのhaskellの行では、$を置き換えることができないのですか()

  14. 14

    このsedコマンドが行に追加される代わりに行を置き換えるのはなぜですか?

  15. 15

    「g」を追加して文字列をsedに置き換えることができるのはなぜですか?

  16. 16

    なぜ✓記号が「1」に置き換えられることがあるのですか?

  17. 17

    これらの関数でzshがハイフンをアンダースコアに置き換えるのはなぜですか?

  18. 18

    htaccessが正しく書き換えられないのはなぜですか

  19. 19

    envsubstが/を置き換えるのはなぜですか

  20. 20

    マージされたデータフレームの値を置き換えることができないのはなぜですか?

  21. 21

    このような文字列のcharを置き換えられないのはなぜですか?

  22. 22

    特定の文字列で\ nを置き換えることができないのはなぜですか?

  23. 23

    Replaceメソッドを使用すると文字列が置き換えられないのはなぜですか?

  24. 24

    シェルでmysqlコマンドを文字列に置き換えることができないのはなぜですか?

  25. 25

    コマンド展開に埋め込まれた改行が空白に置き換えられるのはなぜですか?

  26. 26

    Automatorで、ファイルパスのスラッシュがコロンに置き換えられるのはなぜですか?

  27. 27

    Kotlinの文字列リソースファイルからの文字列であるのに、文字列が置き換えられないのはなぜですか?

  28. 28

    [表示]をクリックすると、常に最初のデータが置き換えられるのはなぜですか?

  29. 29

    スクロールのロゴを置き換えるこのjQueryスクリプトが機能しないのはなぜですか?

ホットタグ

アーカイブ