《C语言笔记:函数指针》
一,函数指针的实质
1,函数指针的实质还是指针,还是指针变量。本身占四个字节(32位系统)。
2,函数指针、数组指针、普通指针之间本身没有区别,区别在于指针指向的东西是个什么玩意。函数指针指向一个函数,数组指针指向一个数组。
3,函数的实质是一段代码,这一段代码在内存中是连续分布的(一个函数的大括号括起来的所有语句将来编译生成的可执行程序是连续的),所以对于函数来说很关键的是函数中的第一句代码的地址,这个地址就是所谓的函数地址,在c语言中用函数名这个符号来表示。
4,结合函数的实质,函数指针其实就是一个普通变量,这个普通变量的类型是函数指针变量类型,它的值就是某个函数的地址(也就是它的函数名这个符号在编译器中所对应的值)。
二,函数指针的书写和分析方法
1,所有的指针变量类型其实本质都是一样的,但是为什么C语言中要去区分它们,写法不一样呢(比如说,int类型指针写做 int *p;数组指针写做 int (*p)[ ];函数指针就写得更复杂了)。因为C语言是一个强类型语言(每一个变量都有自己得变量类型),编译器可以帮助做严格的类型检查,防止不必要得错误。
2,假设有个函数是:void func(void);对应得函数指针就是 void (*pfunc)( void);类型是:(void)(*) (void)。
3,函数名和数组名最大得区别在于:函数名做右值时加不加&效果和意义都是一样得,但是数组名做右值时加不加&就是不一样的。a表示的是数组首元素的首地址,类型是int *;&a表示的是数组首地址,类型是 int (*)[ ]。
#include<stdio.h>
int main(void) { int a[5] = {0}; int *p = a; //类型匹配 int *p1 = &a; //类型不匹配,编译警告 int (*p2)[5] = &a; //类型匹配
return 0;
}
4,写一个复杂的函数指针,比如说strcpy函数 char *strcpy(char *dest,const char *src); char *(*PStrcpy)(char *,const char *);
#include<stdio.h> #include<string.h> int main(void) { int a[5] = {0}; int *p = a; //类型匹配 int *p1 = &a; //类型不匹配,编译警告 int (*p2)[5] = &a; //类型匹配 char *(*pStrcpy)(char *,const char *); char b[10] = {0}; pStrcpy = strcpy; pStrcpy(b,"hello world"); printf(" b = %s \n",b); //hello world }