Java設(shè)計(jì)模式-監(jiān)聽器模式

監(jiān)聽器模式有三個(gè)要素——事件源醇滥、事件對(duì)象、監(jiān)聽器超营。

事件源:顧名思義腺办,事件發(fā)生的源頭,比如點(diǎn)擊的按鈕糟描,屬于被監(jiān)聽的對(duì)象;
事件對(duì)象:這個(gè)經(jīng)常和事件源混淆书妻,它經(jīng)常被用來包裝事件源船响,切記,它畢竟是個(gè)事件躲履,比如點(diǎn)擊事件见间,和事件源的區(qū)別自己感受,木有栗子工猜;
監(jiān)聽器:這個(gè)是監(jiān)聽器模式的核心米诉,定義事件發(fā)生后的動(dòng)作,通常事件對(duì)象作為監(jiān)聽器中定義的函數(shù)入?yún)ⅰ?/p>

下面舉個(gè)簡單的栗子:
故事背景是篷帅,小明是個(gè)不講衛(wèi)生的孩子史侣,他媽媽很擔(dān)心他的健康,規(guī)定必須飯前洗手魏身。
定義一個(gè)熊孩子惊橱。熊孩子就是被監(jiān)聽的對(duì)象,是事件源箭昵,一切事件都是事件源發(fā)出税朴,這似乎是句廢話。

public class Child {
    private String name;
    private RemindListener remindListener;
 
    public Child(String name){
        this.name = name;
    }
    public void eat() {
        if(null!=remindListener){
            remindListener.remind(new RemindWashingHandsEvent(this));
        }
        System.out.println("Child eat...");
    }
 
    public void addListener(RemindListener listener){
        remindListener = listener;
    }
}

接下來是看看事件對(duì)象家制,事件對(duì)象正如上面所述正林,包裝了事件源。我們?cè)谶@里定義一個(gè)飯前洗手事件颤殴。

public class RemindWashingHandsEvent {
    private Child child;
 
    public RemindWashingHandsEvent(Child child){
        this.child = child;
    }
}

事件對(duì)象定義了事件的屬性觅廓、狀態(tài)。
緊接著是定義事件發(fā)生后诅病,監(jiān)聽器的動(dòng)作哪亿,在這里是提醒洗手粥烁。

public class RemindListener {
    public void remind(RemindWashingHandsEvent remindWashingHandsEvent){
        System.out.println("listen to mom, washing hands before eating...");
    }
}

注意,監(jiān)聽器主要封裝了動(dòng)作蝇棉,僅此而已讨阻。
以上代碼,只是為了說明監(jiān)聽器模式原理篡殷,代碼通俗钝吮,不太優(yōu)雅。
下面繼承或?qū)崿F(xiàn)java標(biāo)準(zhǔn)庫板辽,又隨手寫了一對(duì)代碼奇瘦,夜深了,有時(shí)間再解釋劲弦。

public class Kid{
    private String name;
    private List<Listener> liteners;
 
    public Kid(String name) {
        this.name = name;
        this.liteners = Lists.newArrayList();
    }
 
    public void eat(){
 
        for(Listener listener:liteners){
            if(listener instanceof WashingHandsListener){
                WashingHandsListener washingHandsListener = (WashingHandsListener) listener;
                washingHandsListener.fireAfterEventInvoked(new WashingHandsEvent(this,"洗手"));
            }
        }
        System.out.println("吃飯...");
    }
 
    public void addListener(Listener listener){
        liteners.add(listener);
    }
     
}
public class Event extends EventObject {
    /**
     * Constructs a prototypical Event.
     *
     * @param source The object on which the Event initially occurred.
     * @throws IllegalArgumentException if source is null.
     */
    public Event(Object source) {
        super(source);
    }
}
public class WashingHandsEvent extends Event{
    private String eventName;
    /**
     * Constructs a prototypical Event.
     *
     * @param source The object on which the Event initially occurred.
     * @throws IllegalArgumentException if source is null.
     */
    public WashingHandsEvent(Object source,String eventName) {
        super(source);
        this.eventName = eventName;
    }
 
    public String getEventName() {
        return eventName;
    }
 
    public void setEventName(String eventName) {
        this.eventName = eventName;
    }
}
public interface Listener extends java.util.EventListener{
    public void fireAfterEventInvoked(Event event);
}
public class WashingHandsListener implements Listener{
    @Override
    public void fireAfterEventInvoked(Event event) {
        WashingHandsEvent washingHandsEvent = (WashingHandsEvent) event;
        System.out.println("飯前準(zhǔn)備"+ washingHandsEvent.getEventName());
    }
}
public class Test {
    public static void main(String[] args) {
        Kid xiaoming = new Kid("xiaoming");
        xiaoming.addListener(new WashingHandsListener());
        xiaoming.eat();
    }
}

輸出結(jié)果:

image
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末耳标,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子邑跪,更是在濱河造成了極大的恐慌次坡,老刑警劉巖,帶你破解...
    沈念sama閱讀 212,185評(píng)論 6 493
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件画畅,死亡現(xiàn)場離奇詭異砸琅,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)轴踱,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,445評(píng)論 3 385
  • 文/潘曉璐 我一進(jìn)店門症脂,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人淫僻,你說我怎么就攤上這事诱篷。” “怎么了嘁傀?”我有些...
    開封第一講書人閱讀 157,684評(píng)論 0 348
  • 文/不壞的土叔 我叫張陵兴蒸,是天一觀的道長。 經(jīng)常有香客問我细办,道長橙凳,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 56,564評(píng)論 1 284
  • 正文 為了忘掉前任笑撞,我火速辦了婚禮岛啸,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘茴肥。我一直安慰自己坚踩,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,681評(píng)論 6 386
  • 文/花漫 我一把揭開白布瓤狐。 她就那樣靜靜地躺著瞬铸,像睡著了一般批幌。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上嗓节,一...
    開封第一講書人閱讀 49,874評(píng)論 1 290
  • 那天荧缘,我揣著相機(jī)與錄音,去河邊找鬼拦宣。 笑死截粗,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的鸵隧。 我是一名探鬼主播绸罗,決...
    沈念sama閱讀 39,025評(píng)論 3 408
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢(mèng)啊……” “哼豆瘫!你這毒婦竟也來了珊蟀?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,761評(píng)論 0 268
  • 序言:老撾萬榮一對(duì)情侶失蹤外驱,失蹤者是張志新(化名)和其女友劉穎系洛,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體略步,經(jīng)...
    沈念sama閱讀 44,217評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,545評(píng)論 2 327
  • 正文 我和宋清朗相戀三年定页,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了趟薄。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 38,694評(píng)論 1 341
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡典徊,死狀恐怖杭煎,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情卒落,我是刑警寧澤羡铲,帶...
    沈念sama閱讀 34,351評(píng)論 4 332
  • 正文 年R本政府宣布,位于F島的核電站儡毕,受9級(jí)特大地震影響也切,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜腰湾,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,988評(píng)論 3 315
  • 文/蒙蒙 一雷恃、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧费坊,春花似錦倒槐、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,778評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽两残。三九已至,卻和暖如春把跨,著一層夾襖步出監(jiān)牢的瞬間人弓,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,007評(píng)論 1 266
  • 我被黑心中介騙來泰國打工节猿, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留票从,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 46,427評(píng)論 2 360
  • 正文 我出身青樓滨嘱,卻偏偏與公主長得像峰鄙,于是被迫代替她去往敵國和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子太雨,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,580評(píng)論 2 349