日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

c语言宏高级用法,C语言宏高级用法 [总结]

發布時間:2023/12/4 编程问答 22 豆豆
生活随笔 收集整理的這篇文章主要介紹了 c语言宏高级用法,C语言宏高级用法 [总结] 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

1、前言

今天看代碼時候,遇到一些宏,之前沒有見過,感覺挺新鮮。如是上網google一下,順便總結一下,方便以后學習和運用。C語言程序中廣泛的使用宏定義,采用關鍵字define進行定義,宏只是一種簡單的字符串替換,根據是否帶參數分為無參和帶參。宏的簡單應用很容易掌握,今天主要總結一下宏的特殊符號及慣用法。

(1)宏中包含特殊符號:#、##.

(2)宏定義用do{ }while(0)

2、特殊符號#、##

(1)#

When?you?put?a?#?before?an?argument?in?a?preprocessormacro,?the?preprocessor?turns?that?argument?into?a?character?array.

在一個宏中的參數前面使用一個#,預處理器會把這個參數轉換為一個字符數組

簡化理解:#是“字符串化”的意思,出現在宏定義中的#是把跟在后面的參數轉換成一個字符串

#define ERROR_LOG(module) fprintf(stderr,"error: "#module"\n")

ERROR_LOG("add"); 轉換為 fprintf(stderr,"error: "add"\n");

ERROR_LOG(devied =0); 轉換為 fprintf(stderr,"error: devied=0\n");

(2)##

“##”是一種分隔連接方式,它的作用是先分隔,然后進行強制連接。

在普通的宏定義中,預處理器一般把空格解釋成分段標志,對于每一段和前面比較,相同的就被替換。但是這樣做的結果是,被替換段之間存在一些空格。如果我們不希望出現這些空格,就可以通過添加一些##來替代空格。

1 #define TYPE1(type,name) type name_##type##_type

2 #define TYPE2(type,name) type name##_##type##_type

TYPE1(int, c);?轉換為:int  name_int_type ;(因為##號將后面分為 name_ 、type 、 _type三組,替換后強制連接)

TYPE2(int, d);轉換為: int? d_int_type ;(因為##號將后面分為 name、_、type 、_type四組,替換后強制連接)

3、宏定義中do{ }while(0)

第一眼看到這樣的宏時,覺得非常奇怪,為什么要用do……while(0)把宏定義的多條語句括起來?非常想知道這樣定義宏的好處是什么,于是google、百度一下了。

采用這種方式是為了防范在使用宏過程中出現錯誤,主要有如下幾點:

(1)空的宏定義避免warning:

#define foo() do{}while(0)

(2)存在一個獨立的block,可以用來進行變量定義,進行比較復雜的實現。

(3)如果出現在判斷語句過后的宏,這樣可以保證作為一個整體來是實現:

#define foo(x) \

action1(); \

action2();

在以下情況下:

if(NULL == pPointer)

foo();

就會出現action1和action2不會同時被執行的情況,而這顯然不是程序設計的目的。

(4)以上的第3種情況用單獨的{}也可以實現,但是為什么一定要一個do{}while(0)呢,看以下代碼:

#define switch(x,y) {int tmp; tmp="x";x=y;y=tmp;}

if(x>y)

switch(x,y);

else? ?? ? //error, parse error before else

otheraction();

在把宏引入代碼中,會多出一個分號,從而會報錯。這對這一點,可以將if和else語句用{}括起來,可以避免分號錯誤。

使用do{….}while(0)?把它包裹起來,成為一個獨立的語法單元,從而不會與上下文發生混淆。同時因為絕大多數的編譯器都能夠識別do{…}while(0)這種無用的循環并進行優化,所以使用這種方法也不會導致程序的性能降低

4、測試程序

簡單寫個測試程序,加強練習,熟悉一下宏的高級用法。

1 #include

2

3 #define PRINT1(a,b) 4 { 5 printf("print a\n"); 6 printf("print b\n"); 7 }

8

9 #define PRINT2(a, b) 10 do{ 11 printf("print a\n"); 12 printf("print b\n"); 13 }while(0)

14

15 #define PRINT(a) 16 do{17 printf("%s: %d\n",#a,a);18 printf("%d: %d\n",a,a);19 }while(0)

20

21 #define TYPE1(type,name) type name_##type##_type

22 #define TYPE2(type,name) type name##_##type##_type

23

24 #define ERROR_LOG(module) fprintf(stderr,"error: "#module"\n")

25

26 main()

27 {

28 int a = 20;

29 int b = 19;

30 TYPE1(int, c);

31 ERROR_LOG("add");

32 name_int_type =a;

33 TYPE2(int, d);

34 d_int_type =a;

35

36 PRINT(a);

37 if (a >b)

38 {

39 PRINT1(a, b);

40 }

41 else

42 {

43 PRINT2(a, b);

44 }

45 return 0;

46 }

測試結果如下:

5、參考網址

總結

以上是生活随笔為你收集整理的c语言宏高级用法,C语言宏高级用法 [总结]的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。