Java 回调的概念
2015-11-23 15:30
387 查看
回调是一种代码的编写方法。我们最正常的编码逻辑是:
类A需要调用类B的方法b,根据b的返回值,类A再去做一系列赋值啊处理啊之类的工作。
而使用回调的写法:
类A可以把这些后续处理写成一个方法a,然后把A的引用传递给方法b,方法b在做完工作后,就可以直接用A.a来完成A后续的处理工作。
为什么要使用回调呢?下面举一些例子:
1.ajax的写法中我们经常会看到callback,因为发送ajax的请求可能大部分应用可以公用,但是处理请求结果的逻辑每个应用都不一样。这时候我们可以吧发送请求写成公共函数,而把处理结果的逻辑写成回调函数callback,如:ExtAjaxRequestNew(url,param,’callbackfuncName’)。这样,发送请求的逻辑即统一起来了,易于管理维护。
2.常出现在异步场景,比如类A定义发送消息和接收消息函数。发送消息中,把自己注册给异步调用的方法。在异步调用结果出来后,就可以根据注册的那个类得到接收消息函数,从而在此继续进行后续的工作。
3.结合匿名内部类使用,实现多态性。例如数据库接口类DBinterface,必须使用fixMethod方法操作数据库。如果采用继承和上溯造型的写法。就必须为每种操作而创建一个继承类。
如果使用回调方式,可以把抽象方法execute用一个接口(继承方式也可以用接口封装execute而不是使用抽象方法,但只要是用继承还是得写很多类)封装起来,把接口引用通过回调方式注册给fixMethod()。而execute()的实现,结合匿名内部类来实现。这样达到多态的目的,效果和继承方式一样,但显然更为灵活、简洁和优雅。
注意事项:
使用回调时,就必须把引用传递给调用回调函数的对象,这个动作可以称为注册。如果把这个引用作为成员变量,那也能实现注册。但实际场景中,我们很少看到为了回调一个类的方法,而把这个类作为成员变量。也很少看到会直接传递这个类的引用。这是因为侵入性太强—-把一个类的引用传递,那么就暴露了这个类里面的其它对象,可以随意的使用其它的方法。所以,应该把需要回调的那部分函数抽象成接口,在注册时传递接口的引用,这样就保护了类的其它部分细节,达到解耦的目的。
类A需要调用类B的方法b,根据b的返回值,类A再去做一系列赋值啊处理啊之类的工作。
而使用回调的写法:
类A可以把这些后续处理写成一个方法a,然后把A的引用传递给方法b,方法b在做完工作后,就可以直接用A.a来完成A后续的处理工作。
为什么要使用回调呢?下面举一些例子:
1.ajax的写法中我们经常会看到callback,因为发送ajax的请求可能大部分应用可以公用,但是处理请求结果的逻辑每个应用都不一样。这时候我们可以吧发送请求写成公共函数,而把处理结果的逻辑写成回调函数callback,如:ExtAjaxRequestNew(url,param,’callbackfuncName’)。这样,发送请求的逻辑即统一起来了,易于管理维护。
2.常出现在异步场景,比如类A定义发送消息和接收消息函数。发送消息中,把自己注册给异步调用的方法。在异步调用结果出来后,就可以根据注册的那个类得到接收消息函数,从而在此继续进行后续的工作。
3.结合匿名内部类使用,实现多态性。例如数据库接口类DBinterface,必须使用fixMethod方法操作数据库。如果采用继承和上溯造型的写法。就必须为每种操作而创建一个继承类。
fixMethod(){ getConn(); abstract的方法execute(); closeConn(); } class DeleteHandle extends DBinterface{ 实现execute方法为删除; } DBinterface i = new deleteHolder (); i.fixMethod(); class AddHandle extends DBinterface{ 实现execute方法为新增; } DBinterface i = new AddHandle (); i.fixMethod();
如果使用回调方式,可以把抽象方法execute用一个接口(继承方式也可以用接口封装execute而不是使用抽象方法,但只要是用继承还是得写很多类)封装起来,把接口引用通过回调方式注册给fixMethod()。而execute()的实现,结合匿名内部类来实现。这样达到多态的目的,效果和继承方式一样,但显然更为灵活、简洁和优雅。
interface ExeInterface{ execute();} Class template(){ fixMethod(ExeInterface interface){//回调注册 getConn(); interface.execute();//使用回调 closeConn(); } delete(){ fixMethod(new ExeInterface(){//使用匿名内部类 实现execute方法为删除; }) } add(){ fixMethod(new ExeInterface(){//使用匿名内部类 实现execute方法为新增; }) }
注意事项:
使用回调时,就必须把引用传递给调用回调函数的对象,这个动作可以称为注册。如果把这个引用作为成员变量,那也能实现注册。但实际场景中,我们很少看到为了回调一个类的方法,而把这个类作为成员变量。也很少看到会直接传递这个类的引用。这是因为侵入性太强—-把一个类的引用传递,那么就暴露了这个类里面的其它对象,可以随意的使用其它的方法。所以,应该把需要回调的那部分函数抽象成接口,在注册时传递接口的引用,这样就保护了类的其它部分细节,达到解耦的目的。
相关文章推荐
- java对世界各个时区(TimeZone)的通用转换处理方法(转载)
- java-注解annotation
- java-模拟tomcat服务器
- java-用HttpURLConnection发送Http请求.
- java-WEB中的监听器Lisener
- Android IPC进程间通讯机制
- Android Native 绘图方法
- Android java 与 javascript互访(相互调用)的方法例子
- 介绍一款信息管理系统的开源框架---jeecg
- 聚类算法之kmeans算法java版本
- java实现 PageRank算法
- PropertyChangeListener简单理解
- 插入排序
- 冒泡排序
- 堆排序
- 快速排序
- 二叉查找树
- [原创]java局域网聊天系统