这种东西读起来有点绕人,概念很唬人,括号来括号去的,其实就是C语言中数组、指针、函数概念的大合体,最起码不违背这三个概念和他们背后的规则。
简单说就是——函数指针和指针数组的合体,先简单记一下优先级,然后自己往里排顺序即可,推出这个概念是一个循序渐进的没有意外的过程。
万变不离其宗,想分清楚这些概念,只要识别谁是主语谁是修饰主语的定语就行了。
先分辨一下指针函数和函数指针~!
指针函数:所谓函数类型,是指函数返回值的类型,那么指针函数,明显是返回指针的函数!如:
type* func();
为什么用返回值来定义函数的类型呢?想一想,在一个表达式里,返回值也就是你的“类型了,如下例:
int func(){...};
int a = 5,b = 6;
a = b;
a = func();
那么这里的func()应该是返回int型的值,它和b是等价的,也就是说它是int型的。
而函数指针:是指向函数的指针。说白了,他就是一个大小4字节(32位机)的指针,指向函数(即:以函数名为首地址标记的一段连续的内存地址)!
void (*func)(){...};
为了清楚明白的说明,还是来一小段吧:
#include<stdio.h>
//测试指针函数和函数指针,在void*的情况下的区别
void * ptrFunc();//指针函数
//void ptrFunc();//这是绝对行不通的
void func();//函数
void (*funcPtr)();//函数指针
void * ptrFunc(){
printf("I'm ptrFunc()\n");
char* str = (char*)malloc(5*sizeof(char));
str[0] = 'l';
str[1] = 'z';
return str;
}
void func(){
//printf("I'm func\n");
printf("I'm func\n");
}
main(){
char *str;
str = (char*)ptrFunc();//force cast
printf("%s\n",str);
free(str);
str = NULL;
funcPtr = &func;
funcPtr();
}
其中void * ptrFunc();代表返回类型是无类型的指针,不代表不返回,注意void*和void的巨大区别。。。。
那么下边来从基础概念推到出这个结合体——函数指针数组
首先,指针数组的元素是指针fp
*fp;
其次,指针数组是指针*fp 的数组
*fp[4];//[]优先级高,数组fp[4],再结合*,数组里的每个元素是一个指针,这就是指针数组了
最后,要说函数指针了,正常的函数指针是这样来的:
void func(char);
void (*pf)(char) = func;//,相当于把函数名字替换成指针(*fp)
现在要做的事就是把指针数组*fp[4]中的元素——指针*fp[0],*fp[1]....——指向函数
用(*fp[4])来替换(*pf),
在外边放上返回值void和参数(char)来表明函数,数组的元素就是指向void func(char)函数的了
来看小实例:
#include<stdio.h>
double func1(double,double);
double func2(double,double);
double func3(double,double);
double func4(double,double);
int main(void){
double (*fp[4])(double,double);//指向函数double func(double,double)的指针*fp的数组
(fp[0]) = func1;
(fp)[1] = func2;
(fp)[2] = func3;
(fp)[3] = func4;
printf("%lf ",(fp)[0](6.6,4.4));
printf("%lf ",(fp)[1](6.6,4.4));
printf("%lf ",(fp)[2](6.6,4.4));
printf("%lf ",(fp)[3](6.6,4.4));
return 0;
}
double func1(double a,double b){
return a + b;
}
double func2(double a,double b){
return a - b;
}
double func3(double a,double b){
return a * b;
}
double func4(double a,double b){
return a / b;
}
所以,别看”函数指针数组“读起来比较长比较绕,三个概念揉在一起,其实,拆起来也非常简单:
首先,终极主语是数组,你看最后,是个数组吧?
其次,次级主语是指针数组,你看,数组里边存的全是指针吧?
然后,加上定语”函数“,数组里边的这些指针,指向的,都是函数吧?
再然后,就没有然后了~~~~~
分清主语定语,一步一步推出来就完了,错不了!很简单,不是么?
C语言中有很多关键性的概念,只要把原理理解了,很多东西很容易推出来,没必要死记硬背,祝学习愉快~!
对了,”函数指针数组“这东西有什么用?你把上例的那个数组中指针再弄多点,函数也弄多点,弄个几十个,就感觉到有用了,觉得都是0、1、2、3下标,感觉可读性差,弄个枚举代替数字就行了~~~~~
个人肤浅看法,希望对各位有帮助,有质疑请提出~!