[英]C Preprocessor: concatenate macro call with token
我正在嘗試將一個宏調用與一個令牌連接起來以創建一個新的,例如:
#define TEST(X) X ## _TEST
#define CONCAT(X) TEST(X) ## _CONCAT
CONCAT(OK);
然后我用gcc -E
檢查 output ; 我想得到OK_TEST_CONCAT;
但我得到一個錯誤:
error: pasting ")" and "_CONCAT" does not give a valid preprocessing token
如果我刪除##
我沒有得到任何錯誤,但 output 是OK_TEST _CONCAT;
這是一個最小的示例,所以這里最簡單的方法是將所有內容組合在一個宏中,但要知道我不可能擺脫對TEST
的第一次調用。 有沒有辦法刪除那個空間?
謝謝
好吧,從混亂來看,也許我的例子有點太簡單了,那是我的錯。 這是一個更合理的用例:
我希望某個 header 中的所有原型都以該 header 中定義的PREFIX
作為前綴。
#define EXPAND(X) EXPAND_HELPER(X)
#define EXPAND_HELPER(X) X
#define PROTO(NAME) PREFIX ## NAME
#include <proto.h>
#define PREFIX other
int PROTO(test)(int a, int b);
...
我想要的是other.h
中的所有原型都具有這種形式: int other_test(int a, int b);
. 但實際上他們有這種形式: int PREFIX_test(int a, int b);
. 谷歌搜索后我發現我需要強制PREFIX
重新掃描,所以我嘗試了這個:
#define PROTO(NAME) EXPAND(PREFIX) ## NAME
這引發了我的問題。 現在,如果我查看@Lundin 的回答,我可以對其進行調整以提供我想要的內容:
#define PROTO(NAME) PROTO_HELPER(PREFIX, NAME)
#define PROTO_HELPER(PREFIX, NAME) PROTO_EXPAND(PREFIX, NAME)
#define PROTO_EXPAND(PREFIX, NAME) PREFIX ## NAME
謝謝!
在調用使用 ## 或 # 的類函數宏之前,必須展開所有預處理器標記。 因為 ## 或 # 在宏擴展之前應用。 在您的情況下TEST(X)
僅將X
擴展為TEST(OK)
,然后預處理器嘗試將TEST(OK)
與_CONCAT
粘貼,這將不起作用。 對於每次連接標記的嘗試,您必須首先在 ## 之前展開所有宏,這是由強制重新掃描/替換的額外輔助宏完成的。
給定#define TEST(X) X ## _TEST
的人為解決方案是這樣的:
#define CONCAT(X) EXPAND_HELPER(TEST(X)) // expands TEST(X) to TEST(OK)
-->
#define EXPAND_HELPER(X) CONCAT_HELPER(X, _CONCAT) // expands TEST(OK) to OK_TEST
-->
#define CONCAT_HELPER(X,Y) X ## Y
那是:
// NOTE: contrived solution, avoid
#define TEST(X) X ## _TEST
#define CONCAT_HELPER(X,Y) X ## Y
#define EXPAND_HELPER(X) CONCAT_HELPER(X, _CONCAT)
#define CONCAT(X) EXPAND_HELPER(TEST(X))
...
int CONCAT(OK) = 1; // becomes int OK_TEST_CONCAT = 1;
一個更簡單的解決方案是:
#define CONCAT(X) X ## _TEST ## _CONCAT
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.