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

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

带参数的宏定义

發(fā)布時(shí)間:2023/12/20 编程问答 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 带参数的宏定义 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
不是進(jìn)行簡(jiǎn)單的字符串替換,還要進(jìn)行參數(shù)替換。其定義的一般形式為

   #define 宏名(參數(shù)表) 字符串

  字符串中包含在括弧中所指定的參數(shù)。如:

  #define S(a,b) a*b
  area=S(3,2);

定義矩形面積S,a 和 b 是邊長(zhǎng)。在程序中用了S(3,2),把3、2分別代替宏定義中的形式參數(shù)a、b,即用 3*2 代替 S(3,2)。因此賦值語(yǔ)句展開(kāi)為

  area=3*2;

  對(duì)帶參的宏定義是這樣展開(kāi)轉(zhuǎn)換的:在程序中如果有帶實(shí)參的宏(如S(3,2)),則按 #define 命令行中指定的字符串從左到右進(jìn)行置換。如果串中包含宏中的形參(如a、b),則將程序語(yǔ)句中相應(yīng)的實(shí)參(可以是常量、變量或表達(dá)式)代替形參。如果宏定義中的字符串中的字符不是參數(shù)字符(如 a*b 中的 * 號(hào)),則保留。這樣就形成了置換的字符串,見(jiàn)右圖。

【例1】

#define PI 3.1415926
#define S(r) PI*r*r

main(){
???float a,area;
???a=3.6;
???area=S(a);
???printf("r=%f\narea=%f\n",a,area);
}

運(yùn)行結(jié)果如下:

r=3.600000
area=40.715038

  賦值語(yǔ)句"area=S(a)";經(jīng)宏展開(kāi)后為

  area=3.1415926*a*a;

  說(shuō)明:

  (1) 對(duì)帶參數(shù)的宏的展開(kāi)只是將語(yǔ)句中的宏名后面括號(hào)內(nèi)的實(shí)參字符串代替 #define 命令行中的形參。例1中語(yǔ)句中有S(a),在展開(kāi)時(shí),找到 #define 命令行中的 S(r),將 S(a) 中的實(shí)參 a 代替宏定義中的字符串“PI*r*r”中的形參r,得到PI*a*a。這是容易理解而且不會(huì)發(fā)生什么問(wèn)題的。但是,如果有以下語(yǔ)句:

  area=S(a+b);

這時(shí)把實(shí)參 a+b 代替 PI*r*r 中的形參r,成為

  area=PI*a+b*a+b;

請(qǐng)注意在 a+b 外面沒(méi)有括弧,顯然這與程序設(shè)計(jì)者的原意不符。原意希望得到

  area=PI*(a+b)*(a+b);

為了得到這個(gè)結(jié)果,應(yīng)當(dāng)在定義時(shí),在字符串中的形式參數(shù)外面加一個(gè)括弧。即

  #define S(r) PI*(r)*(r)

在對(duì) S(a+b) 進(jìn)行宏展開(kāi)時(shí),將 a+b 代替 r,就成了

  PI*(a+b)*(a+b)

這就達(dá)到了目的。

  (2) 在宏定義時(shí),在宏名與帶參數(shù)的括弧之間不應(yīng)加空格,否則將空格以后的字符都作為替代字符串的一部分。例如,如果有

  #define S (r) PI*r*r

被認(rèn)為 S 是符號(hào)常量(不帶參的宏名),它代表字符串“(r) PI*r*r”。如果在語(yǔ)句中有

  area=S (a);

則被展開(kāi)為

  area=(r) PI*r*r (a);

顯然不對(duì)了。

  有些讀者容易把帶參數(shù)的宏和函數(shù)混淆。的確,它們之間有一定類似之處,在調(diào)用函數(shù)時(shí)也是在函數(shù)名后的括弧內(nèi)寫(xiě)實(shí)參,也要求實(shí)參與形參的數(shù)目相等。但是帶參的宏定義與函數(shù)是不同的。主要有:

  (1) 函數(shù)調(diào)用時(shí),先求出實(shí)參表達(dá)式的值,然后代入形參。而使用帶參的宏只是進(jìn)行簡(jiǎn)單的字符替換。例如上面的 S(a+b),在宏展開(kāi)時(shí)并不求 a+b 的值,而只將實(shí)參字符“a+b”代替形參r。

  (2) 函數(shù)調(diào)用是在程序運(yùn)行時(shí)處理的,為形參分配臨時(shí)的內(nèi)存單元。而宏展開(kāi)則是在編譯前進(jìn)行的,在展開(kāi)時(shí)并不分配內(nèi)存單元,不進(jìn)行值的傳遞處理,也沒(méi)有“返回值”的概念。

  (3) 對(duì)函數(shù)中的實(shí)參和形參都要定義類型,二者的類型要求一致,如不一致,應(yīng)進(jìn)行類型轉(zhuǎn)換。而宏不存在類型問(wèn)題,宏名無(wú)類型,它的參數(shù)也無(wú)類型,只是一個(gè)符號(hào)代表,展開(kāi)時(shí)代入指定的字符串即可。宏定義時(shí),字符串可以是任何類型的數(shù)據(jù)。例如:

  #define CHAR1 CHINA  (字符)
  #define a 3.6     (數(shù)值)

CHAR1 和 a 不需要定義類型,它們不是變量,在程序中凡遇 CHAR1 均以 CHINA 代之;凡遇 a 均以 3.6 代之,顯然不需定義類型。同樣,對(duì)帶參的宏:

  #define S(r) PI*r*r

r 也不是變量,如果在語(yǔ)句中有 S(3.6),則展開(kāi)后為 PI*3.6*3.6,語(yǔ)句中并不出現(xiàn)r。當(dāng)然也不必定義 r 的類型。

  (4) 調(diào)用函數(shù)只可得到一個(gè)返回值,而用宏可以設(shè)法得到幾個(gè)結(jié)果。

【例2】

#define PI 3.1415926
#define CIRCLE(R,L,S,V) L=2*PI*R;S=PI*R*R;V=4.0/3.0*PI*R*R*R

main(){
???float r,l,s,v;
???scanf("%f",&r);
???CIRCLE(r,l,s,v);
???printf("r=%.2f,l=%.2f,s=%.2f,v=%.2f\n",r,l,s,v);
}

經(jīng)預(yù)編譯宏展開(kāi)后的程序如下:

main(){
???float r,l,s,v;
???scanf("%f",&r);
???l=2*3.1415926*r;s=3.1415926*r*r;v=4.0/3.0*3.1415926*r*r*r;
???printf("r=%.2f,l=%.2f,s=%.2f,v=%.2f\n",r,l,s,v);
}

  請(qǐng)注意,實(shí)參 r 的值已知,可以從宏帶回3個(gè)值(l,s,v)。其實(shí),只不過(guò)是字符代替而已,將字符r代替R,l代替L,s代替S,v代替V,而并未在宏展開(kāi)時(shí)求出l、s、v的值。

  (5) 使用宏次數(shù)多時(shí),宏展開(kāi)后源程序長(zhǎng),因?yàn)槊空归_(kāi)一次都使程序增長(zhǎng),而函數(shù)調(diào)用不使源程序變長(zhǎng)。

  (6) 宏替換不占運(yùn)行時(shí)間,只占編譯時(shí)間。而函數(shù)調(diào)用則占運(yùn)行時(shí)間(分配單元、保留現(xiàn)場(chǎng)、值傳遞、返回)。

  一般用宏來(lái)代表簡(jiǎn)短一的表達(dá)式比較合適。有些問(wèn)題,用宏和函數(shù)都可以。如:

  #define MAX(x,y) (x)>(y)?(x):(y)
  main(){
    int a,b,c,d,t;
    ┊
    t=MAX(a+b,c+d);
    ┊
  }

  賦值語(yǔ)句展開(kāi)后為

  t=(a+b)>(c+d)?(a+b):(c+d);

注意:MAX不是函數(shù),這里只有一個(gè) main 函數(shù),在 main 函數(shù)中就能求出 t 的值。

  這個(gè)問(wèn)題也可用函數(shù)來(lái)求:

  int max(int x,int y){
    return(x>y?x:y);
  }

  main(){
    int a,b,c,d,t;
    ┊
    t=max(a+b,c+d);
    ┊
  }

max是函數(shù),在 main 函數(shù)中調(diào)用 max 函數(shù)才能求出 t 的值。

  請(qǐng)仔細(xì)分析以上兩種方法。

  如果善于利用宏定義,可以實(shí)現(xiàn)程序的簡(jiǎn)化,如事先將程序中的“輸出格式”定義好,以減少在輸出語(yǔ)句中每次都要寫(xiě)出具體的輸出格式的麻煩。

【例3】

#define PR printf
#define NL "\n"
#define D "%d"
#define D1 D NL
#define D2 D D NL
#define D3 D D D NL
#define D4 D D D D NL
#define S "%s"

main(){
???int a,b,c,d;
???char string[]="CHINA";
???a=1;b=2;c=3;d=4;
???PR(D1,a);
???PR(D2,a,b);
???PR(D3,a,b,c);
???PR(D4,a,b,c,d);
???PR(S,string);
}

運(yùn)行時(shí)輸出以下結(jié)果:

1
12
123
1234
CHINA

  程序中用 PR 代表 printf。以 NL 代表執(zhí)行一次“換行”操作。以 D 代表輸出一個(gè)整型數(shù)據(jù)的格式符。以 D1 代表輸出完1個(gè)整數(shù)后換行,D2 代表輸出2個(gè)整數(shù)后換行,D3 代表輸出3個(gè)整數(shù)后換行,D4 代表輸出4個(gè)整數(shù)后換行。以 S 代表輸出一個(gè)字符串的格式符。可以看到,程序中寫(xiě)輸出語(yǔ)句就比較簡(jiǎn)單了,只要根據(jù)需要選擇已定義的輸出格式即可,連 printf 都可以簡(jiǎn)寫(xiě)為PR。

  可以參照例3,寫(xiě)出各種輸入輸出的格式(例如實(shí)型、長(zhǎng)整型、十六進(jìn)制整數(shù)、八進(jìn)制整數(shù)、字符型等),把它們單獨(dú)編成一個(gè)文件,它相當(dāng)一個(gè)“格式庫(kù)”,用 #include 命令把它“包括”到自己所編的程序中,用戶就可以根據(jù)情況各取所需了。顯然在寫(xiě)大程序時(shí),這樣做是很方便的。


版權(quán)聲明:此文章為廠商在線—軟件直銷網(wǎng)(www.soft568.com)原創(chuàng),如需轉(zhuǎn)載請(qǐng)保留此鏈接,并勿隨意改動(dòng)文章內(nèi)容!





不帶參數(shù)的宏定義

http://www.doc88.com/p-992520052502.html


不帶參數(shù)的宏定義

總結(jié)

以上是生活随笔為你收集整理的带参数的宏定义的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。