免責聲明:我已經(jīng)看過類似于Stringification of a macro value的問題的答案.
考慮以下測試程序:
#include <stdio.h>#define QUOTE(str) #str#define EXPAND_AND_QUOTE(str) QUOTE(str)#define MACRO HelloWorldint main() { printf("%s\n", EXPAND_AND_QUOTE(MACRO)); printf("%s\n", QUOTE(MACRO)); #undef MACRO printf("%s\n", EXPAND_AND_QUOTE(MACRO)); printf("%s\n", QUOTE(MACRO));}
該程序的輸出是:
HelloWorldMACROMACROMACRO
期望的輸出是
HelloWorldMACROMACRO
有沒有辦法重新定義我的宏(即不是MACRO的元宏)來獲得所需的輸出?
特別是,我希望第三個printf應該相當于:
printf("%s\n", QUOTE());
也就是說,我希望將未定義的宏擴展為“虛無”,然后將“虛無”傳遞給引用函數(shù).
解決方法:
這在標準C中是不可能的.
在宏替換期間,令牌可能會發(fā)生四件事.它可以保持不變,可以用替換值替換,它可以與另一個令牌連接,并且可以進行字符串化.
如果MACRO沒有變化,則無法區(qū)分這兩種情況:
#undef MACROprintf("%s\n", EXPAND_AND_QUOTE(MACRO));#define FOO MACROprintf("%s\n", EXPAND_AND_QUOTE(FOO));
一旦FOO在后者中被替換,我們有兩種情況:在一種情況下,我們有MACRO,因為它沒有變化.另一方面,我們有MACRO,因為它取代了FOO.在那之后,行為必須相同.但問題要求需要不同的行為,“”對于前者,“MACRO”對后者.由于相同的行為不能產(chǎn)生不同的結果,因此這不起作用. (但更多關于以下內(nèi)容.)
第二種可能性,即用另一個值替換,不會發(fā)生,因為沒有定義MACRO.
第三種可能性僅產(chǎn)生一些新的令牌,例如FOOMACRO.然而,盡管我們可以選擇第一部分,但我們不能選擇后一部分,因此我們無法知道將產(chǎn)生什么標記,并且根據(jù)MACRO是否定義,我們可能無法使用它.
第四種可能性與第三種可能性相同,我們生產(chǎn)“MACRO”并且不能使用它.
我對此做的唯一模糊的希望是產(chǎn)生兩個令牌,一個是讓令牌被替換而另一個不被取代的結果.例如,我們可以產(chǎn)生一種情況,其中,鑒于上述MACRO的非定義和FOO的定義,EXPAND_AND_QUOTE(MACRO)在輔助宏的擴展鏈中產(chǎn)生兩個標記SomethingMACRO和SomethingMACRO,而EXPAND_AND_QUOTE(FOO) )生產(chǎn)SomethingFOO和SomethingMACRO.這是可能的,但那么我們?nèi)绾翁幚磉@兩個令牌呢?我們可以對兩者進行字符串化,然后在運行時將它們與strcmp進行比較.但是,我不認為在編譯時可以做任何事情.此外,它無法區(qū)分FOO被定義為#define FOO FOO的情況;如果我們成功地比較上述令牌,就會產(chǎn)生“”,但是要求要求它產(chǎn)生“FOO”.
來源:https://www.icode9.com/content-4-408751.html聯(lián)系客服