回调函数与函数指针

回调函数与函数指针


用途

1、许多窗口就是通过回调函数来实现的,不同的按钮执行不同的函数

2、菜单处理

3、消息或事件机制也可以看作是一种回调机制

 

函数回调的实现方式

一般由函数指针实现,将函数的地址作为参数传递给调用他的函数,当函数执行到主调函数时,通过函数指针(即地址)找到被调用的函数,实现被调函数的功能,用函数回调的方式配合void *可以增加代码的通用性,只要函数指针所指向函数类型确定,就可以将同类型的函数的地址传递给主调函数,传递不同函数地址,用同一个主调函数实现不同的功能,可以通过以下代码来说明

#include <stdio.h>
#include <math.h>

//枚举类型声明
typedef enum ERR1
{
	DAYU,
	XIAOYU
}ERR;

//函数声明
ERR F_Comp(const void *a, const void *b);
ERR I_Comp(const void *a, const void *b);
int GetResult(const void *a, const void *b, ERR (*Comp)(const void *n, const void *b));


int main()
{
	int a =9;
	int b = 2;
	float c = 89.0;
	float d = 38.0;

	GetResult((void *)(&c), (void *)(&b), I_Comp);	//回调函数为整型比较函数
	printf("\n-------------------------------------------\n");
	GetResult((void *)&d, (void *)&c, F_Comp);		//回调函数为浮点数比较函数
	printf("\n");
	
	return 0;
}

//函数的第三个参数为函数指针,传递回调函数的地址
int GetResult(const void *a, const void *b, ERR (*Comp)(const void *n, const void *b))
{
	//ERR err;

	Comp(a, b);										//通过函数指针调用函数

	return 0;
}

//整型数的比较
ERR I_Comp(const void *a, const void *b)
{
	if(*(int *)a > *(int *)b)						//强制类型转换
	{
		printf("%d > %d\n", *(int *)a, *(int *)b);
		return DAYU;
	}
	else
	{
		printf("%d <= %d\n", *(int *)a, *(int *)b);
		return XIAOYU;
	}
}

//浮点数的比较
ERR F_Comp(const void *a, const void *b)
{
	if(fabsf(*(float *)a - *(float *)b) > 0.00001)
	{
		printf("%f > %f\n", *(float *)a, *(float*)b);
		return DAYU;
	}
	else
	{
		printf("%f <= %f\n", *(float *)a, *(float *)b);
		return XIAOYU;
	}
}

主函数中给GetResult函数传递的函数地址分别为I_Comp、F_Comp,所以通过统一的函数GetResult获得了整型数和浮点数的比较结果

注意到GetResult函数参数都是void *型的,代表他可以接受任意类型的参数,而函数指针所指向函数的类型的参数接受的也是void *类型的参数,至于具体处理什么样的数据,则是由回调函数自己来定义的,I_Comp、F_Comp函数在函数体内部分别将void *型的数据强制转换成了整型指针和浮点型指针,明确了所要操作的数据类型,所以GetResult函数根本不关心回调函数是如何实现的,它只要知道回调函数的入口地址就可以了,不同的回调函数入口地址不同,自然实现的功能也就不同,但这样做统一了函数接口的

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值