2011-03-18 99 views
5

我碰到一個斷言的這個例子來格式化,並想知道的#是什麼時:什麼是#用%s

#define ASSERT(x) if (!(x)) { \ 
    int *p = NULL; \ 
    DBGPRINTF("Assert failed: [%s]\r\n Halting.", #x); \ 
    *p=1; \ 
    } 

回答

4

#x是字符串化指令

#define Stringify(x) #x

表示Stringify(abc)將被替換爲​​

#define initVarWithItsOwnName(x) const char* p = #x 

int main() 
{ 
    initVarWithItsOwnName(Var); 
    std::cout << Var; //will print Var 
} 
9

這是「stringize」預處理運算符。

它將令牌作爲參數傳遞給宏參數x並將它們轉換爲字符串文字。

​​
3

#是預處理器的"stringizing" operator。它將宏參數轉換爲字符串文字。如果您調用ASSERT(foo >= 32),則在評估宏時,#x將擴展爲"foo >= 32"

2

這是一個稱爲stringification的預處理器功能。它

用實際參數的文本文本替換[宏參數],轉換爲字符串常量。

2

#是在第6.10.3.2節(C99)和第16.3.2節中定義的串化運算符。 (C++ 03)

它將宏參數轉換爲字符串文字而不擴展參數定義。

如果產生的更換是不是一個有效的字符串文字中, 行爲是不確定。 #運算符的評估順序是未指定

例如,在語法上,字符串文字中反斜線字符的出現被限制爲轉義序列。

在下面的例子:

1  #define mkstr(x) # x 
2  char *p = mkstr(a \ b); 
     /* "a \ b" violates the syntax of string literals */ 

#的運算符的結果不必是"a \ b"

+1

是否有任何情況下「替換結果不是有效的字符串文字」?我想不出任何。 – 2011-03-18 16:16:02

+0

@James McNellis:在「新C標準」中找到一個例子,查看我的帖子。 – 2011-03-18 16:29:32

+0

有趣。我對「預處理令牌序列的拼寫」(來自C++)的理解是編譯器需要執行任何必要的轉義,所以'mkstr(「a」)'會產生一個「」而不是「 「」 一 「」'。也許這不適用於無關的非空白標記? – 2011-03-18 16:36:34