当前位置: 首页 > article >正文

C指针之舞——指针探秘之旅(2)

❤博客主页:折枝寄北-CSDN博客

❤专栏:C语言学习专栏

在上一篇博客文章:C指针之舞——指针探秘之旅-CSDN博客中,我们学习了字符指针,指针数组,数组指针,数组传参和指针传参等内容,下面进一步学习C语言指针。

1.函数指针数组

函数指针就是一个指针,指针中所保存的地址中的内容是一个函数,同之前说过的数组指针相似,函数指针的定义为:

返回类型  (* 指针名) (函数参数)   //eg: int (*pc) (intx,iny)

与数组指针一样,当定义函数指针的时候,* 需要和指针名打括号相结合,( )的优先级高于 * ,不打括号编译器自动会将 指针名 与( )相结合,如 int * pa (int x,int y) ,这样的话便是一个名为pa的函数,函数参数为 int x,int y,函数的返回类型时 int *

通过一个例子来认识一下函数指针数组:

(*(void (*)())0)();

1.先看 void ( * ) ( )  ,这是一个标准的函数指针,函数返回类型为void,无函数参数
2.再看蓝色括号,该括号的代表强制转换,例如:(float)3 指的是将int类型的3转换为float类型,在这里指的是将int类型的0转换为函数指针类型
3.看蓝色括号前面的 * ,这里是解地址符,指找到地址是0的函数
4.红色的括号包括着地址是0的这个函数(函数指针此时是0),后面再跟着一个绿色的括号,相当于调用函数
所以该代码是一次函数调用,调用的是一个返回类型为void,无函数参数,函数名为0 的一个函数

2.回调函数

定义:回调函数是利用函数指针调⽤的函数,通俗来讲,只要是一个函数参数里面有函数指针,都可以被称为回调函数。

例如:完成一个简易的计算器,要求输入1代表计算加法,2代表计算减法,3代表计算乘法,4代表计算除法,0代表退出计算器,选择1 2 3 4其中一个后输入要计算的两个数字,返回计算结果

当不使用回调函数的代码如下:

#include <stdio.h>
int add(int a, int b)
{
	return a + b;
}
int sub(int a, int b)
{
	return a - b;
}
int mul(int a, int b)
{
	return a * b;
}
int div(int a, int b)
{
	return a/b;
}
int main()
{
	int x, y;
	int input = 0;
	int ret = 0;
	do
	{
		printf("***********************\n"); 
		printf("* 0:退出 1:add  2:sub *\n");
		printf("*     3:mul   4.div   *\n");
		printf("***********************\n");
		printf("请选择:");
		scanf("%d", &input);
		switch (input)
		{
			case 1:
				printf("输入操作数:");
				scanf("%d %d", &x, &y);
				ret = add(x, y);
				printf("ret = %d\n", ret);
				break;
			case 2:
				printf("输入操作数:");
				scanf("%d %d", &x, &y);
				ret = sub(x, y);
				printf("ret = %d\n", ret);
				break;
			case 3:
				printf("输入操作数:");
				scanf("%d %d", &x, &y);
				ret = mul(x, y);
				printf("ret = %d\n", ret);
				break;
			case 4:
				printf("输入操作数:");
				scanf("%d %d", &x, &y);
				ret = div(x, y);
				printf("ret = %d\n", ret);
				break;
			case 0:
				printf("退出程序\n");
				break;
			default:
				printf("选择错误\n");
				break;
		}
	} while (input);
	return 0;
}

可以看到有多个重复的步骤,增加了无意义的工作量,这是我们可以注意到这四个函数(add,sub,mul,div)的函数参数都是两个int类型的变量,返回值也都是int,那么我们就可以使用回调函数来简化代码。

简化代码如下:

#include <stdio.h>
void menu()
{
	printf("*************************\n");
	printf("    1:add       2:sub \n");
	printf("    3:mul       4:div \n");
	printf("    0:exit \n");
	printf("*************************\n");
}
int Add(int x, int y)
{
    return x + y;
}
int Sub(int x, int y)
{
    return x - y;
}
int Mul(int x, int y)
{
    return x * y;
}
int Div(int x, int y)
{
    return x / y;
}
//回调函数 
void Callback(int (*pfun)(int,int))
{
	int x = 0;
	int y = 0;
	int ret = 0;
	printf("请输入两个数字:");
	scanf("%d %d",&x,&y);
	ret = pfun(x,y);
	printf("结果为:%d\n",ret);
}
int main()
{
	int input = 0;
    do
    {
    	menu();
    	printf("请输入你的选择:----->");
    	scanf("%d",&input);
    	switch(input)
    	{
    		case 1:
    			Callback(Add);
    			break;
    		case 2:
    			Callback(Sub);
    			break;
			case 3:
				Callback(Mul);
    			break;
			case 4:
				Callback(Div);
    			break;
			case 0:
				printf("退出计算器!");
    			break;	
    		default:
    			break;
		}
	}while(input);
    return 0;
} 


http://www.kler.cn/a/408467.html

相关文章:

  • Load-Balanced-Online-OJ(负载均衡式在线OJ)
  • Transformer详解及衍生模型GPT|T5|LLaMa
  • 使用 LSTM(长短期记忆网络) 模型对时间序列数据(航空旅客人数数据集)进行预测
  • 2.2_3 纠错编码—海明码
  • Spring |(四)IoC/DI配置管理第三方bean
  • STL——string类常用接口说明
  • CentOS 7安装SSHFS 实现远程主机目录 挂载为本地目录
  • 计网-命令行实现收发邮件
  • 【算法】BFS解决最短路径问题
  • Python脚本消费多个Kafka topic
  • WebStorm 2024.3/IntelliJ IDEA 2024.3出现elementUI提示未知 HTML 标记、组件引用爆红等问题处理
  • Spring Boot OA管理系统:提升企业运营效率
  • 【Stable Diffusion】 超大尺寸绘制、分区控制,详解Tiled Diffusion VAE插件功能
  • 人工智能大趋势下软件开发的未来
  • 【论文复现】BERT模型解读与简单任务实现
  • RabbitMQ3:Java客户端快速入门
  • MariaDB面试题及参考答案
  • 【OpenGL】GLFW环境配置 + 扩展GLFW使其可以成为MFC子窗口
  • C0033.在Ubuntu中配置clion的环境
  • 数据集-目标检测系列- 安全背心 检测数据集 safety_vests >> DataBall
  • docker desktop上下载的镜像传到虚拟机上使用
  • Python编程整理汇总(基础汇总版)
  • sed使用扩展正则表达式时, -i 要写在 -r 或 -E 的后面
  • Window11系统下修改Anaconda3默认安装虚拟环境在C盘问题
  • C++设计模式——Singleton单例模式
  • Flask服务封装+Docker服务部署