Java回调机制解析
生活随笔
收集整理的這篇文章主要介紹了
Java回调机制解析
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
模塊之間總是存在這一定的接口,從調用方式上看,可以分為三類:同步調用、回調和異步調用。同步調用是一種阻塞式調用,也是我們在寫程序中經常使用的;回調是一種雙向的調用模式,也就是說,被調用的接口被調用時也會調用對方的接口,這句話可能有點繞,等文章后面舉例說明;異步調用是一種類似消息或事件的機制,解決了同步阻塞的問題,舉例來講:A通知B后,他們各走各的路,互不影響,不用像同步調用那樣,A通知B后,非得等到B走完后,A才繼續走?;卣{是異步的基本,因此下面著重說回調機制。 我們暫且不討論回調的一些名詞和運行機制,首先說為什么會存在回調這樣一種調用?同步和異步機制的出現不必多說,大家心知肚明,那回調機制為什么會出現呢?在我們現實生活中,有如下這樣場景:有一位老板很忙,他沒有時間盯著員工干活,然后他告訴自己的雇員,干完當前這些事情后,告訴他干活的結果。這個例子其實是一個回調+異步的例子,再舉一個例子,A程序員寫了一段程序a,其中預留了回調函數接口,并封裝好了該程序,程序員B讓a調用自己的程序b中的一個方法,于是,他通過a中的接口回調自己b中的方法,到這里你可能似懂非懂了,后面會繼續說明回調的出現原因。接下來我們把上面例子變成代碼,看到網上很多人最后搞混了異步和回調,因此例子中不加入異步調用。(注意:回調可不是解決什么調用時間過長問題,那是異步!) 首先創建一個回調接口,讓老板得告知干完活如何找到他的方式:留下老板辦公室地址: [java] view plaincopy package net.easyway.test; /** * 此接口為聯系的方式,不論是電話號碼還是聯系地址,作為 * 老板都必須要實現此接口 * @author Administrator * */ public interface CallBackInterface { public void execute(); } 創建回調對象,就是老板本人,因為員工干完活后要給他打電話,因此老板必須實現回調接口,不然員工去哪里找老板? [java] view plaincopy package net.easyway.test; /** * 老板是作為上層應用身份出現的,下層應用(員工)是不知道 * 有哪些方法,因此他想被下層應用(員工)調用必須實現此接口 * @author Administrator * */ public class Boss implements CallBackInterface { @Override public void execute() { System.out.println("收到了!!" + System.currentTimeMillis()); } } 創建控制類,也就是員工對象,他必須持有老板的地址(回調接口),即使老板換了一茬又一茬,辦公室不變,總能找到對應的老板。 [java] view plaincopy package net.easyway.test; /** * 員工類,必須要記住,這是一個底層類,底層是不了解上層服務的 * @author Administrator * */ public class Employee { private CallBackInterface callBack = null; //告訴老板的聯系方式,也就是注冊 public void setCallBack(CallBackInterface callBack){ this.callBack = callBack; } //工人干活 public void doSome(){ //1.開始干活了 for(int i=0;i<10;i++){ System.out.println("第【" + i + "】事情干完了!"); } //2.告訴老板干完了 callBack.execute(); } } 測試類代碼: [java] view plaincopy package net.easyway.test; public class Client { public static void main(String[] args) { Employee emp = new Employee(); //將回調對象(上層對象)傳入,注冊 emp.setCallBack(new Boss()); //開啟控制器對象運行 emp.doSome(); } } 上面這個例子,大家可以和程序員A和程序員B的那個例子結合對照下。 看了上面的例子,有的人可能認為,這不是面向接口的編程嗎?怎么會是回調,你再好好想想,咱們面向接口的編程的調用關系?在三層中,當業務層調用數據層時,是不需要把業務層自身傳遞到數據層的,并且這是一種上層調用下層的關系,比如我們在用框架的時候,一般直接調用框架提供的API就可以了,但回調不同,當框架不能滿足需求,我們想讓框架來調用自己的類方法,怎么做呢?總不至于去修改框架吧。許多優秀的框架提幾乎都供了相關的接口,我們只需要實現相關接口,即可完成了注冊,然后在合適的時候讓框架來調用我們自己的類,還記不記得我們在使用Struts時,當我們編寫Action時,就需要繼承Action類,然后實現execute()方法,在execute()方法中寫咱們自己的業務邏輯代碼,完成對用戶請求的處理。由此可以猜測,框架和容器中會提供大量的回調接口,以滿足個性化的定制。 不知道上面這個例子懂了沒有?我們現在可以想象Filter和Interceptor的區別了,這兩者其中最大的一個區別是Filter是基于回調函數,需要容器的支持,沒有容器是無法回調doFilter()方法,而Interceptor是基于Java的反射機制的,和容器無關。那到此是否又將反射和回調搞混了呢?請見我講Java動態代理的博客《以此之長,補彼之短----AOP(代理模式)》。 總之,要明確的一點是,首先要搞清回調函數出現的原因,也就是適用場景,才能搞清楚回調機制,不然事倍功半。 最后,再舉一例,為了使我們寫的函數接近完美,就把一部分功能外包給別人,讓別人個性化定制,至于別人怎么實現不管,我唯一要做的就是定義好相關接口,這一設計允許了底層代碼調用高層定義的子程序,增強程序靈活性,和反射有著異曲同工之妙,我覺得這才是回調的真正原因,以上是我個人一些理解,望討論! 原文: http://blog.csdn.net/pi9nc/article/details/23169357
轉載于:https://www.cnblogs.com/jiftle/p/7241287.html
總結
以上是生活随笔為你收集整理的Java回调机制解析的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 静态工厂
- 下一篇: ContestHunter暑假欢乐赛 S