函數指針有意思的地方在於,它使用從0到n-1這個n個連續的整數下標直接映射到函數上。
和前面同樣,咱們也是類比着定義普通指針數組來定義函數指針數組。首先,考慮一個浮點數指針數組,數組的長度爲10.咱們都知道用下面的形式來定義:
float * pFloatArray[10];
從形式上分析,用中括號明確了是定義指針變量仍是定義指針數組這個語義。用數字10明確了這個數組能容納多少個函數指針這個語義。形式上看,中括號是緊接在指針名稱的後面再中括號裏面是一個須要在編譯時期間就可以肯定的常數。
如今咱們來類比函數指針數組的定義,定義一個指向函數指針類型爲:float (*)(float,float)的函數指針數組,數組長度爲10.正確的形式爲:
float(* pFunctionArray[10])(float,float)
從形式上看,這種定義方式和定義普通指針的定義方式是一致的:都是在指針名稱後面緊接着一箇中括號,而後裏面是一個編譯期間可以肯定的常數。這種形式上的一致性,能夠方便咱們對形式的記憶,進而達到對內容的理解。
下面是一個例子程序:
- /*
- *Author:Choas Lee
- *Date:2012-02-28
- */
- #include<stdio.h>
- float add(float a,float b){return a+b;}
- float minus(float a,float b){return a-b;}
- float multiply(float a,float b){return a*b;}
- float divide(float a,float b){return a/b;}
- int main()
- {
- float(*func_pointers[4])(float,float)={add,minus,multiply,divide};
- int i=0;
- float a=10.0,b=5.0;
- for(i=0;i<4;i++)
- {
- printf("result is %f\n",func_pointers[i](a,b));
- }
- return 0;
- }
如下爲對應的運行結果:
- result is 15.000000
- result is 5.000000
- result is 50.000000
- result is 2.000000
從哲學角度講,形式過於複雜的話,仍是抽象的層次過低。若是咱們使用多層次的抽象,這樣最上層的表示就會簡化不少。這就是引入typedef的緣由,使用typedef能夠簡化函數指針的定義,由於typedef能夠定義新的類型:
一樣,在使用typedef定義函數指針類型的時候,也和普通的使用typedef引入新類型的方式不同。咱們和前面同樣對照着普通的定義方式來學習:
typedef int bool;
這在C語言中很經常使用,因爲C語言中沒有bool類型,這樣定義以後能夠從形式上引入一個bool類型,提升代碼可讀性。因此形式爲:
typedef 已知類型 新類型;
如今咱們要將float (*)(float,float)類型聲明爲一種新類型,按照上面的方式,貌似爲:typedef float(*)(float,float) fpType;然而,前面的經驗告訴咱們應該這樣定義啊:
typedef float(*fpType)(float,float);
這樣咱們就能夠用fpType來表示float (*)(float,float)這種類型了。因此定義一個新的指向float (*)(float,float)類型的指針變量的時候,咱們就能夠採用下面這種形式了:
fpType pFunction;
在定義函數指針數組的時候能夠這樣定義:
fpType pFunctions[10];
在定義函數指針類型參數時能夠這樣定義:
void func(fpType pFunction);
在定義函數指針類型的返回值時能夠這樣定義:
fpType func(int a);
如今咱們再來看一下,unix中的那個signal函數,其形式爲:
void (*signal)(int signo,void (*func)(int)))(int);
如今咱們定義一個類型爲:
typedef void (*pSgnType)(int);
這樣上面的函數就能表達爲:
pSgnType signal(int signo,pSgnType func);
這樣是否是看起來清爽多了。
其實上面的signal函數也能這樣定義:
首先引入新類型:
typedef void SgnType(int)
而後signal函數的聲明改成:
SgnType *signal(int signo,SgnType *func);
按照前面對這些形式的解釋,理解這個應該沒難度~~
如今在引入最後一個例子,關於使用typedef來簡化函數指針定義的:
- /*
- *Author:Choas Lee
- *Date:2012-02-29 00:25
- */
- #include<stdio.h>
- #include<stdlib.h>
- #include<string.h>
- float add(float a,float b){return a+b;}
- float minus(float a,float b){return a-b;}
- float multiply(float a,float b){return a*b;}
- float divide(float a,float b){return a/b;}
- typedef float (*pArithmeticOperations)(float,float);
- typedef float ArithmeticOperations(float,float);
- int main()
- {
- pArithmeticOperations pao=add;
- pArithmeticOperations paos[4]={add,minus,multiply,divide};
- ArithmeticOperations *ao=add;
- ArithmeticOperations *aos[4]={add,minus,multiply,divide};
- float a=10.0,b=5.0;
- float result=0.0;
- int i=0;
- result=pao(a,b);
- printf("the result of pao is %f\n",result);
- printf("the results of paos are:\n");
- for(i=0;i<4;i++)
- {
- result=paos[i](a,b);
- printf("result=%f\n",result);
- }
- result=ao(a,b);
- printf("\n\nthe result of ao is :%f\n",result);
- printf("the results of aos are:\n");
- for(i=0;i<4;i++)
- {
- result=aos[i](a,b);
- printf("result=%f\n",result);
- }
- return 0;
- }
輸出結果爲:
- result=15.000000
- result=5.000000
- result=50.000000
- result=2.000000
- the result of ao is :15.000000
- the results of aos are:
- result=15.000000
- result=5.000000
- result=50.000000
- result=2.000000
時間不早了,該回去睡覺了~
引用:
Function pointer tutorial.