溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

什么是宏定義函數

發(fā)布時間:2020-08-06 10:24:23 來源:億速云 閱讀:278 作者:Leah 欄目:互聯網科技

這篇文章將為大家詳細講解有關什么是宏定義函數,文章內容質量較高,因此小編分享給大家做個參考,希望大家閱讀完這篇文章后對相關知識有一定的了解。

在預處理時,對程序中所有出現的“宏名”,都用宏定義中的字符串去代換,這稱為“宏代換”或“宏展開”。宏定義是由源程序中的宏定義命令完成的。宏代換是由預處理程序自動完成的。若字符串是表達式,我們稱之為函數式宏定義。

我們以下面兩行代碼為例,展開描述:

函數式宏定義:#define MAX(a,b) ((a)>(b)?(a):(b))

普通函數 :MAX(a,b) { return a>b?a:b;}

(1)函數式宏定義的參數沒有類型,預處理器只負責做形式上的替換,而不做參數類型檢查,所以傳參時要格外小心。

(2)函數式宏定義要注意格式,尤其是括號。

若上面的宏定義式函數寫成#define MAX(a,b) (a>b?a:b)省去內層括號,宏展開后由于運算符優(yōu)先級,運行結果出錯;若上面的宏定義式函數省去外層括號,宏定義為 ++MAX(a,b),則宏展開就成了 ++(a)>(b)?(a):(b),運算優(yōu)先級也是錯了。

(3)若函數參數為表達式,則普通函數的調用與函數式宏定義的替換過程是不一樣的。

普通函數調用時先求實參表達式的值再傳給形參,如果實參表達式有Side Effect,那么這些SideEffect只發(fā)生一次。例如MAX(++a, ++b),如果MAX是普通函數,a和b只增加一次。但如果MAX函數式宏定義,則要展開成k = ((++a)>(++b)?(++a):(++b)),a和b就不一定是增加一次還是兩次了。所以若參數是表達式,替換函數式宏定義時一定要仔細看好。

(4)調用真正函數的代碼和調用函數式宏定義的代碼編譯生成的指令不同。

如果MAX是個普通函數,那么它的函數體return a > b ? a : b; 要編譯生成指令,代碼中出現的每次調用也要編譯生成傳參指令和call指令。而如果MAX是個函數式宏定義,這個宏定義本身倒不必編譯生成指令,但是代碼中出現的每次調用編譯生成的指令都相當于一個函數體,而不是簡單的幾條傳參指令和call指令。所以,使用函數式宏定義編譯生成的目標文件會比較大。

優(yōu)勢:

首先,函數調用會帶來額外的開銷,它需要開辟一片??臻g,記錄返回地址,將形參壓棧,從函數返回還要釋放堆棧,這種開銷會降低代碼效率,而使用宏定義則在代碼規(guī)模和速度方面比函數更勝一籌;

其次,函數的參數必須被聲明為一種特定的類型,所以它只能在類型合適的表達式上使用,我們如果要比較兩個浮點型的大小,就不得不再寫一個專門針對浮點型大小的比較函數,反之,上面的宏定義可以用于整型、長整型、單浮點型、雙浮點型及其他可以用“<”操作符比較值大小的類型,也就是說,宏與類型無關。

關于什么是宏定義函數就分享到這里了,希望以上內容可以對大家有一定的幫助,可以學到更多知識。如果覺得文章不錯,可以把它分享出去讓更多的人看到。

向AI問一下細節(jié)

免責聲明:本站發(fā)布的內容(圖片、視頻和文字)以原創(chuàng)、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI