宏定义基本用法
宏定義
不帶參數
宏定義又稱為宏代換、宏替換,簡稱“宏”。
格式:
#define 標識符 字符串其中的標識符就是所謂的符號常量,也稱為“宏名”。
預處理(預編譯)工作也叫做宏展開:將宏名替換為字符串。
掌握”宏”概念的關鍵是“換”。一切以換為前提、做任何事情之前先要換,準確理解之前就要“換”。
例:
#define Pi 3.1415926把程序中出現的Pi全部換成3.1415926
帶參數(宏函數)
宏名之后帶括號的宏被認為是宏函數。用法和普通函數一樣,只不過在預處理階段,宏函數會被展開。優點是沒有普通函數保存寄存器和參數傳遞的開銷,展開后的代碼有利于CPU cache的利用和指令預測,速度快。缺點是可執行代碼體積大。
和不帶參數的宏定義一樣,除了一般的字符串替換,還要做參數代換。
格式:
#define <宏名> (<參數表>) <宏體>例如:
#define S(a,b) a*barea=S(3,2);第一步被換為area=a * b; ,第二步被換為area=3 * 2;
(1)實參如果是表達式容易出問題
例如:
#define S(r) r*rarea=S(a+b);第一步換為area=r * r;,第二步被換為area=a+b * a+b;
正確的宏定義是#define S(r) ((r)*(r))
(2)帶參宏一般用法
例如:
#define MIN(A, B) A < B ? A : Bint a = 2 * MIN(3, 4); printf("%d", a);展開結果:
int a = 2 * MIN(3, 4); //=> int a = 2 * 3 < 4 ? 3 : 4; //=> int a = 6 < 4 ? 3 : 4; //=> int a = 4;正確如下:
#define MAX(a,b) ((a)>(b)?(a):(b))則遇到MAX(1+2,value)則會把它替換成:
((1+2)>(value)?(1+2):(value))
(3)有參宏定義中#的用法
需要注意的是凡宏定義里有用’#’或’##’的地方宏參數是不會再展開,被當做字符串處理
#define STR(str) #str“#”號用于把宏定義中的參數兩端加上字符串的”“
比如,這里 STR(my#name) 會被替換成”my#name”
(4)有參宏定義中##的用法
例如:
#define WIDE(str) L##str則會將形參str的前面加上L
比如:
WIDE(“abc”)就會被替換成L”abc”
如果有:
#define FUN(a,b) vo##a##b()那么FUN(id ma,in)會被替換成void main()
多行宏定義
每一次換行都必須要有 “ \ ”結尾,末尾行不需要“ \ ” 結尾。
例如:
#define doit(m,n) for(int i=0;i<(n);++i)\ {\ m+=i;\ } #define WARN_IF(EXP) \do { if (EXP) \fprintf (stderr, "Warning: " #EXP "\n"); } \while (0)WARN_IF (x == 0);會被擴展成:
do { if (x == 0)fprintf (stderr, "Warning: " "x == 0" "\n"); } while (0); #define VAR_TO_STR(var)\({\std::string name = (#var);\int pos = 0;\int length = 0;\length = name.length();\pos = name.find_last_of(':',length);\if ( pos == -1 )\{\pos = 0;\name = name.substr(pos,length);\}\else\{\name = name.substr( pos + 1,length);\}\(name);\})std::string str = VAR_TO_STR(VDAD::RRR) 展開后:
int main() {std::string ss =({std::string name = ("VDAD::RRR");int pos = 0;int length = 0;length = name.length();pos = name.find_last_of(':',length);if ( pos == -1 ){pos = 0;name = name.substr(pos,length);}else{name = name.substr( pos + 1,length);}(name);});cout << ss<< endl;return 0; }輸出為:
相關鏈接
1.C語言宏的特殊用法和幾個坑
2.C/C++ 宏定義
總結
- 上一篇: 【二分】LED
- 下一篇: mip-link 组件功能升级说明