[英]Preprocessor swaps arguments
我有一些代碼需要文本表示形式的值和與十六進制表示形式相同的值。 我需要兩者,但是要消除潛在的錯誤源,我只想指定一次值,然后讓預處理器來處理它。
這是一個例子。
int[] v = { 0x01, 0x02 };
LPCTSTR s = L"0102";
預處理器合並在此方面提供了強大的幫助。 這是相同的代碼,但是現在通過預處理器命令。
#define STRING2(x) #x
#define STRING(x) STRING2(x)
#define _S(t) _T(STRING2(t))
#define _H(t) 0x ## t
#define _VS(a,b) _S(a) _S(b)
#define _VH(a,b) _H(a),_H(b)
LPCTSTR s = _VS(01, 02);
int[] v = { _VH(01, 02) };
前處理器生成的代碼如下所示:
int[] v = { 0x01,0x02 };
LPCTSTR s = L"01" L"02";
但是我仍然在重復我的數據。 所以,我嘗試這個。
#define ARGUMENTS 01, 02
LPCTSTR s = _VS(ARGUMENTS);
int[] v = { _VH(ARGUMENTS) };
現在,預處理器代碼已損壞!
int[] v = { 0x01, 02,0x };
LPCTSTR s = L"01" L;
請注意,第二個自變量以及應與之一起使用的令牌部分已交換或丟失。 但為什么?
VS2010幫助頁面對我沒有太大幫助。 它告訴我,隱含運算符在宏擴展上放了一些約束。 擴展宏參數的原因很可能是愚蠢的。 但是我怎樣才能使它工作呢?
額外的測試表明,肯定是隱式運算符阻止了宏的進一步擴展。 因此,我需要一種首先擴展參數然后使用隱式運算符的方法。 好主意? 現在如何!
歡迎任何建議。
我覺得您應該將您的定義重寫為XMacros 。 這是一種巧妙的技術,可以讓您編寫一個包含數據定義的文件(通常以.def
擴展名),如下所示:
VAL(01)
VAL(02)
比您簡單地定義一個適當的宏,並包含以獲得所需的結構,就像這樣:
#define VAL(x) _H(x),
int[] v = {
#include "values.def"
};
#undef VAL
#define VAL(x) _S(x)
LPCTSTR s =
#include "values.def"
;
#undef VAL
由於ARGUMENTS
仍然是單個值,一個東西,你在兩個輸出清楚地看到- ARGUMENTS
作為單個參數處理,然后第二個空參數的處理(GCC實際上是更helpfuls並扔掉與預處理error: macro "_VS" requires 2 arguments, but only 1 given
)。
要實現您想要的,請嘗試以下操作:
#define MK_STRING_INT_PAIR(a,b,sname,vname) \
LPCTSTR sname=_VS(a,b); \
int[] vname={_VH(a,b)};
MK_STRING_INT_PAIR(01,02,s,v)
[編輯]如果需要兩個以上的值,請編寫一個簡短的程序來生成帶有宏的.h文件,該文件位於以下行:
#define MK_PAIRS_2(sname,vname,v0,v1) ...
#define MK_PAIRS_3(sname,vname,v0,v1,v3) ...
#define MK_PAIRS_128(sname,vname,....
生成后,您將無需依賴_VS,_VH幫助程序宏
(我感覺在C ++ 11中,我有潛力使用可變參數模板和char []類型的constexpr-s來執行此操作,但是現在我沒有時間去探索它)。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.