随便讲讲我的理解。
callback概念解释
这是非常普通的一次方法调用(method call):
一般来说,method()的调用耗时很短,也就几毫秒。但如果method()内部涉及磁盘IO或者method()干脆就是网络调用(网络IO),可能就比较耗时了。至于多久才称得上「耗时」,不太好定义。当前案例中,不妨理解为:客户端无法忍受得到最终结果所耗费的时间。
如何解决耗时操作呢?你可能很容易就想到「异步」:
这里的「异步」,指的是狭隘的「开启一个子线程」。但是上面这个图 并不完整 ,原本的代码里method()是有result的:
你可能很容易就想到了两种方案:
但实际上,对于调用方而言两种方式是一样的,它都要等待这个method耗时操作完成才能收到result,然后才能执行后面的domething later操作。
于是产生了矛盾:
比较好的处理方式是:
既然do something依赖于method的result,那么do something应该和method共同处理,所以我把do something挪到method内部怎么把do something挪到method里面呢?
由于do something的需求各种各样,是不确定的,不能在method里写死。为了能让method()帮我们执行自定义的操作, method()必须再提供一个入参:
callback()具有特异性,只有调用方才知道要做什么样的处理,所以要定义在调用侧,也就是和main()在一块。
callback与设计模式
callback和策略模式很像,但个人觉得还是细微差别,主要是出发点不同。
这是callback:
这是策略模式:
你要说策略模式「有call有back」,所以也算callback,其实也说得通...但两者出发点是不同的。当前案例可能看不出来,再举一个例子可能更好理解。
比如跨系统的callback:
这个时候你很难称之为「策略模式」。
还有观察者模式也是如此,看起来也和callback很像,但出发点也多少有点区别。观察者模式出发点是当事件源发生改变时收到通知,而callback更像是有妥协的步骤拆分。
当然,还是那句话,你要是觉得这几个本质是一样的,那就这么认为也无妨,个人觉得没必要死扣定义。
callback与IO模型
很多人也学习过NIO和AIO,特别是AIO,定义了一个CompletionHandler接口:
当某个I/O操作完成时,会自动回调completed(),我们实现completed()完成自己要做的操作。
总的来说,callback可大可小,宏观的有JVM内的回调函数、系统间的回调接口,微观的有操作系统的回调机制,甚至脱口秀也有callback。
博主最近新写的小册,图文并茂,通俗易懂:
还有2024年新写的【设计模式那些事儿】: