Callback回调机制知识大全

回调函数是一种编程机制,允许函数A在执行时调用由函数B提供的代码。它常用于事件处理、异步编程和接口交互。回调可以是函数指针或函数对象,通过传递这些回调,函数B可以在适当的时候调用特定的处理逻辑。本文通过商店购物的例子和程序概念解释了回调的工作原理,并探讨了其在排序、事件监听等场景的应用。
摘要由CSDN通过智能技术生成

举个例子:你到一个商店买东西,刚好你要的东西没有货,于是你在店员那里留下了你的电话,过了几天店里有货了,店员就打了你的电话,然后你接到电话后就到店里去取了货。在这个例子里,你的电话号码就叫回调函数,你把电话留给店员就叫登记回调函数,店里后来有货了叫做触发了回调关联的事件,店员给你打电话叫做调用回调函数,你到店里去取货叫做响应回调事件。

另一种说法:

这个是程序上的概念。
本质上是叫别人做事,传进去的额外信息。

比如,A叫B做事,根据粒度不同,可以理解成A函数调用B函数,或者A类使用B类,或者A组件使用B组件等等。反正就是A叫B做事。

当B做这件事情的时候,自身的需要的信息不够,而A又有。就需要A从外面传进来,或者B做着做着主动向外面申请。对于B来说,一种被动得到信息,一种是主动去得到信息,有人给这两种方式术语,叫信息的push,和信息的pull。

接着,A调用B,A向B传参数。int max(int a, int b); 要使用这函数max, 得到两者最大的值, 外面就要传进来a, b。这个好理解。

再跟着,就来到计算机中比较诡异的地方。也就是代码(code)和数据(data)的统一,这是一个槛,如果不打通这个,很多概念就不清楚。我们常常说计算机程序分成code和data两部分。很多人就会觉得,code是会运行的,是动的,data是给code使用,是静态的,这是两种完全不同的东西。

其实code只是对行为的一种描述,比如有个机器人可以开灯,关灯,扫地。跟着我要机器人开灯,扫地,关灯。如果跟机器人约定好,0表示开灯,1表示关灯,2表示扫地。我发出指令,0 1 2 1 0。跟着就可以控制机器人开灯,扫地,关灯。再约定用二进制表示,两位一个指令,就有一个数字串,0001110100,这个时候0001110100这串数字就描述了机器人的一系列动作,这个就是从一方面理解是code,可以它可以控制机器人的行为。但另一方面,它可以传递,可以记录,可以修改,也就是数据。只要大家都协商好,code就可以编码成data, 将data解释运行的时候,也变成了code。

这个地方扯开了。我自己是不区分code和data的,统一称为信息。那既然int max(int a, int b)中int,double等表示普通data的东西可以传递进去,凭什么表示code的函数就不可以传进去了。有些语言确实是不区分的,它的function(表示code)跟int, double的地位是一样的。这种语言就为函数是第一类值。

但问题是,有些语言是不能存储函数的,不能动态创建函数的,不能动态销毁函数的。(这里函数是已经是广义的了,用来表示代码code)。只能存储一个指向函数的指针,这种语言称为函数是第二类值。

另外有些语言不单可以传递函数,函数里面又用到一些外部信息(包括code, data)。那些语言可以将函数跟函数所用到的信息一起传递存储。这种将函数和它所用的信息作为一个整体,就为闭包。

再次声明,将代码和数据打通,统一起来,是一个槛。过了这个槛,很多难以理解的概念就会清晰很多。比如一些修改自身的程序啊,数据驱动啊,先设计数据再写程序等等。过了这山,眼界就开阔了。

来到这里,其实已经没有什么好说的了。回调函数也就是是A让B做事,B做着做着,信息不够,不知道怎么做了,就再让外面处理。

比如排序,A让B排序,B是会做排序,但排序需要知道哪个比哪个大,这点B自己不知道,就需要A告诉它。而这种判断那个大,本身是一种动作,既然C语言中不可以传进第一值的函数,就设计成传递第二值的函数指针,这个函数指针就是A传向B的信息,用来表示一个行为。这里本来A调用B的,结果B又调用了A告诉它的信息,也就叫callback。

再比如A让B监听系统的某个消息,比如敲了哪个键。跟着B监听到了,但它不知道怎么去处理这个消息,就给外面关心这个消息,又知道怎么去处理这个消息的人去处理,这个处理过程本事是个行为,既然这个语言不可以传递函数,又只能传一个函数指针了。跟着有些人有会引申成,什么注册啊,通知啊等等等。假如B做监听,C, D, E, F, G, H告诉B自己有兴趣知道这消息,那B监听到了就去告诉C,D,E,F,G等人了,这样通知多人了,就叫广播。

其实你理解了,根本不用去关心术语的。术语是别人要告诉你啊,或者你去告诉人啊,使用的一套约定的词语。本质上就个东西,结果会有很多术语的。

跟着再将回调的概念进化,比如某人同时关心A,B,C,D,E,F事件,并且这些事件是一组的,比如敲键盘,鼠标移动,鼠标点击等一组。将一组事件结合起来。在有些语言就变成一个接口,接口有N个函数。有些语言就映射成一个结构,里面放着N个函数指针。跟着就不是将单个函数指针传进去,而是将接口,或者函数指针的结构传进去。这些根据不同的用途,有些人叫它为代理啊,监听者啊,观察者啊等等。


再简单点说:

回调函数的主要功能就是提供统一的接口以及事件的通知。如果你是从事middleware,框架,提供API编程的,那么你肯定少不了要使用回调函数。

所谓提供统一接口或者事件的通知即:当发生某一事件或者出现某一个状态之后必定会进行某种操作。但是这个操作又不能写死,不同的环境不同的程序会有不同的实现,也就是说提供接口的人不想把逻辑写死,而是由调用接口的人来实现逻辑。这也就是回调函数的主要功能。

 

 

回调函数,唯一途径就是传递函数指针。通过这个函数指针来调用真正的函数。

 

 

下面使用代码说明究竟如何实现回调函数,并通过这个例子来说明回调函数的作用:

 

 

  1. /** 
  2. filename: mytimer.h 
  3. description: 
  4. 这里我用一个闹钟静态库mytimer.a来演示回调函数的实现方法 
  5. */  
  6. #ifndef MYTIMER_H  
  7. #define MYTIMER_H  
  8. typedef void (*tmfun)(tumfun );  
  9. typedef struct{  
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值