在 Linux 內(nèi)核中,經(jīng)常會(huì)看到do{} while(0)這樣的語句,許多人開始都會(huì)疑惑,認(rèn)為do{} while(0)毫無意義,因?yàn)樗粫?huì)執(zhí)行一次,加不加do{} while(0)效果是完全一樣的,其實(shí)do {}while(0)的用法主要用于宏定義中。
這里用一個(gè)簡(jiǎn)單的宏來演示:
#defineSAFE_FREE(p)do{free(p);p=NULL;}while(0)
假設(shè)這里去掉do...while(0),即定義SAFE_DELETE為:
#defineSAFE_FREE(p)free(p);p=NULL;
那么以下代碼:
if(NULL!=p) SAFE_DELETE(p) else .../*dosomething*/
會(huì)被展開為:
if(NULL!=p) free(p);p=NULL; else .../*dosomething*/
展開的代碼中存在兩個(gè)問題。
(1)、因?yàn)?if 分支后有兩個(gè)語句,導(dǎo)致 else 分支沒有對(duì)應(yīng)的 if,編譯失敗。
(2)、假設(shè)沒有 else 分支,則 SAFE_FREE 中的第二個(gè)語句無論 if 測(cè)試是否通過,都會(huì)執(zhí)行。
的確,將SAFE_FREE的定義加上{}就可以解決上述問題了,即:
#defineSAFE_FREE(p){free(p);p=NULL;}
這樣,代碼:
if(NULL!=p) SAFE_DELETE(p) else .../*dosomething*/
會(huì)被展開為:
if(NULL!=p) {free(p);p=NULL;} else .../*dosomething*/
但是,在 C 程序中,每個(gè)語句后面加分號(hào)是一種約定俗成的習(xí)慣,那么,如下代碼:
if(NULL!=p) SAFE_DELETE(p); else .../*dosomething*/
將被擴(kuò)展為:
if(NULL!=p) {free(p);p=NULL;}; else .../*dosomething*/
這樣,else 分支就又沒有對(duì)應(yīng)的 if 了,編譯將無法通過。假設(shè)用了do {} while(0),情況就不一樣了,同樣的代碼會(huì)被展開為:
if(NULL!=p) do{free(p);p=NULL;}while(0); else .../*dosomething*/
不會(huì)再出現(xiàn)編譯問題。do while(0)的使用完全是為了保證宏定義的使用者能在不出現(xiàn)編譯錯(cuò)誤的情況下使用宏,它不對(duì)其使用者做任何假設(shè)。
審核編輯:劉清
-
C語言
+關(guān)注
關(guān)注
180文章
7614瀏覽量
137408 -
LINUX內(nèi)核
+關(guān)注
關(guān)注
1文章
316瀏覽量
21700
原文標(biāo)題:C語言-宏定義中使用do {...} while(0)到底圖個(gè)啥
文章出處:【微信號(hào):嵌入式那些事,微信公眾號(hào):嵌入式那些事】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。
發(fā)布評(píng)論請(qǐng)先 登錄
相關(guān)推薦
評(píng)論