c語言裡的巨集(翻譯)2

2022-02-12 04:07:46 字數 1805 閱讀 7024

object-like 巨集

object-like巨集是乙個簡單的標識,在編譯器會被一段**代替。由於它看上去很像乙個在**中被使用的資料域,所以管它叫object-like巨集。最常使用該型別巨集的場合是:用乙個指定符號代替乙個數字常量。

使用「#define」指令定義乙個巨集,#define之後跟乙個巨集名,巨集名之後跟一段巨集內容,編譯器在預處理時會把巨集名用巨集內容替代。舉例來說,

#define buffer_size 1024

定義了乙個名為buffer_size的巨集,buffer_size指代的內容是數字1024。如果該#define語句之後的某處出現了buffer_size

foo = (char*) malloc ( buffer_size);

預處理器就能識別出buffer_size是乙個巨集,並用1024代替它,在編譯器看來,上面這句和下面這句是一摸一樣的

foo = (char*) malloc (1024);

處於一些約定俗成的規則,巨集名字一般全部大寫。當所有表示巨集的符號都大寫時,閱讀**會變得比較容易。

巨集內容在#define行的行末結束,當然,如果你一定要把乙個巨集定義寫成多行,方法也是有的,那就是用反斜槓把回車符轉義。當巨集被展開時,轉義過的回車會變成同一行,比如

#define numbers 1, \

2, \

3int x = ;

==> int x = ;

這種寫法最常出現在錯誤資訊裡的行號表示。
巨集定義沒有強制的約束,括號並不是一定要配對,也不要求你的巨集展開後就是合法的c語句。
c語言的預處理器順序掃瞄**,巨集定義在你寫過它之後才生效,所以,下面的**輸入到預處理器裡後:
foo = x;

#define x 4

bar = x;

產生這樣的**:
foo = x;

bar = 4;

預處理器擴充套件乙個巨集時,巨集的擴充套件會遞迴進行,直到沒有符號可以代替為止。比如,
#define tablesize bufsize

#define bufsize 1024

tablesize

==> bufsize

==> 1024

tablesize被展開為bufsize,然後bufsize被展開為1024.
注意bufsize在tablesize之後定義,所以tablesize展開後就是bufsize,而不會繼續檢查bufsize是否可以展開。直到使用tablesize時,預處理器看到bufsize這個符號,才會繼續掃瞄尋找bufsize的內容。
如果你在**的同一地點改變了bufsize的定義,那麼情況看起來會有些違反直觀:
#define bufsize 1020

#define tablesize bufsize

#undef bufsize

#define bufsize 37

tablesize展開後是37,因為tablesize先展開為bufsize, 然後bufsize展開為37。
如果乙個巨集展開後包含了該巨集本身,不管是直接包含還是間接包含,巨集展開都會立刻停止。該項規則防止了無限遞迴的產生。更多詳情參看自包含巨集。

c語言裡的巨集(翻譯)4

巨集引數 function like巨集可以帶引數,就好像函式帶引數一樣。定乙個乙個帶引數巨集的時候,把引數插入到兩個括號之間,就好像定義函式的引數一樣。這就是該類巨集被稱為function like巨集的原因。巨集引數必須是合法的c標識,由逗號和空格隔開。呼叫帶引數的巨集,你可以在寫完巨集名之後插...

C語言巨集裡 的用法

c 和c 中的巨集 macro 屬於編譯器預處理的範疇,屬於編譯期概念 而非執行期概念 下面對常遇到的巨集的使用問題做了簡單總結。關於 和 define warn if exp do while 0 那麼實際使用中會出現下面所示的替換過程 warn if divider 0 被替換為 do whil...

c語言裡,關於巨集定義的使用

巨集定義最關鍵的是要注意它只是乙個文字替換,不注意的話,很容易引起歧義,看下面一段 include define m x x x int main int a,b 3 a m b 2 printf d n a return 0 這裡的 m 是想要得到 x 的平方,而在程式中呼叫的引數為 b 2 原本...