(C/C++学习)16.函数指针
2024-08-30 19:18:45
说明:函数指针,顾名思义就是指向函数的指针。C/C++中函数名的本质其实就是一段代码段空间的首地址。
1.定义
如下的 pf 就是一个函数指针,指向所有返回类型为 int,并带有两个 const int 参数的函数。需要注意的是 *pf 两边的括号不能少,否则下面定义就变成声明一个函数 pf,其返回类型为 int *, 带有两个 const int 参数。
int (*pf)(const int, const int);
2.取别名
如果每次都像上面那样来声明一个函数指针,那样就显得太复杂了,我们可以通过取别名的方式来简化声明复杂程度,如下:
typedef int (*cmpFun)(const int, const int);
这样,cmpFun 就成了一种数据类型,可以用它来声明和定义形如上面 pf 那样的函数指针,比如:
cmpFun pf = someFunction;
cmpFun pf = &someFunction;
下面是一个测试代码:
#include <stdio.h> void myCmp(int a,int b)
{
printf("%d\t%d\n",a,b);
} typedef void (*PF)(int a, int b);
PF pf = myCmp; int main(void)
{
(*pf)(1,2);
pf(1,2);
//两种访问方式都没问题
return 0;
}
3.函数名作为地址的用法
上面提到了,函数名的本质是一个地址,那如果我们拿到这个地址,是否可以直接调用相应的函数呢?答案是肯定的!如下代码,先打印出函数名所代表的地址,然后将其强转成 PF 函数指针类型,然后在对其进行函数的调用。
#include <stdio.h> void myCmp(int a,int b)
{
printf("%d\t%d\n",a,b);
} typedef void (*PF)(int a, int b);
PF pf = myCmp; int main(void)
{
pf(1,2);
printf("%p\t%p\n",myCmp,&myCmp);
((PF)(0x00401610))(1,2);
return 0;
}
上面代码的打印结果为:
1 2
00401610 00401610
1 2
4.回调函数
当函数作为参数而发起的调用函数的过程,就叫作函数的回调。函数的回调其实也是利用了函数指针这一概念。下面是一个回调示例:
#include <stdio.h> void myCmp(int a,int b)
{
printf("%d\t%d\n",a,b);
}
void prin(void (*p)(int a,int b))
{
p(1,2);
} int main(void)
{
prin(myCmp);
return 0;
}
5.函数指针数组
如下定义一个返回值和参数皆为 void 的函数指针数组:
void (*funcArray[N])(void);
函数指针的一个用法出现在菜单驱动系统中。例如程序可以提示用户输入一个整数值来选择菜单中的一个选项。用户的选择可以做函数指针数组的下标,而数组中的指针可以用来调用函数。下面是一个程序示例:
#include <stdio.h>
void func1()
{
printf("void func1()\n");
}
void func2()
{
printf("void func2()\n");
}
void func3()
{
printf("void func3()\n");
} int main(void)
{
int i = 0;
void (*p[3])(void) = {func1,func2,func3};
for(;i<3;i++)
(p[i])();
return 0;
}
6.拓展
(*(void(*) ()) 0)()
思考以上代码的意义!
最新文章
- 不同java 版本的新功能
- maven nexus 3 third party 构件上传
- 平衡二叉树(AVL)java实现
- js中iframe的用法
- redis内存管理代码的目光
- scanf函数与scanf_s函数
- ZOJ 3696 Alien&#39;s Organ 概率论 泊松分布
- 单元测试框架 unittest 的运行方法if __name__ == &#39;__main__&#39;: unittest.main()
- Screen命令安装使用教程
- udt通信java
- LeetCode 142. Linked List Cycle II 判断环入口的位置 C++/Java
- L2-027. 名人堂与代金券
- (转)mysql升级5.5.20时遇到的问题:1548-Cannot load from mysql.proc. The table is probably corrupted
- MySQL8.0手动安装心得。
- python-day15函数递归
- Vibrator震动
- 我在GitHub Pages托管静态博客啦~
- 并发编程---线程 ;python中各种锁
- USACO16OPEN_248&;&;USACO16OPEN_262144_KEY
- 005-环境安装【docker、fabric】