設計模式-觀察者模式__java

來源:互聯網
上載者:User
前言 先簡要說說觀察者模式的定義與組成吧。 觀察者模式定於與組成 通俗來講,觀察者模式定義了一種一對多的依賴關係,讓多個觀察者對象同時監聽某一個主題對象。當這個主題對象在狀態上發生變化時,通知所有觀察者對象,讓它們可以主動的更新自己。觀察者模式主要分為四部分:抽象主題角色;抽象觀察者角色;具體主題角色;具體觀察者角色。
接下來看看我自訂的觀察者模式吧。
自訂觀察者模式 先說說需求吧: 通過觀察者模式來實現一個簡單的訊息訂閱。 接下來說說具體的設計抽象: 想想觀察者的主要部分,大致可以抽象出這樣幾個類:Subject(主題),Observer(觀察者),ConcreateSubject(具體的主題角色),ConcreteObserver(具體的觀察者角色)
抽象出這幾個類後,可以畫出如下的類圖:

具體的代碼實現: 抽象角色: Subject:
public interface Subject {     /**     * 訊息訂閱     * @param observer     */    public void subscribe(Observer observer);     /**     * 廣播訊息     */    public void publish();     /**     * 退訂某個服務     * @param observer     */    public void unSubscribe(Observer observer);     /**     * 退訂全部服務     */    public void unSubscribeAllServers(); }
AbstractSubject:
public abstract class AbstractSubject implements Subject {         //觀察者List    private List<Observer> observers;     public AbstractSubject() {        this.observers = Lists.newArrayList();    }     public void subscribe(Observer observer) {        if (null == observer) {            return;        }        observers.add(observer);    }     public void publish() {        for (Observer observer : observers) {            observer.update(this);        }    }     public void unSubscribe(Observer observer) {        System.out.println("unsubscribe...\n");        observers.remove(observer);    }     public void unSubscribeAllServers() {        observers.clear();    }}
Observer:
public interface Observer {     public void update(Subject subject);}
具體角色: ConcreateSubject:
public class ConcreateSubject extends AbstractSubject {     //訊息狀態    private int status;     //訊息主題    private String subject;     public ConcreateSubject(String subject) {        super();        status = Status.NOT_SEND.getStatus();        this.subject = subject;    }     //訊息狀態變更    public void changed(int newStatus) {        this.status = newStatus;        publish();    }     public String getSubject() {        return subject;    }     public int getStatus() {        return status;    }}
ConcreateObserver:

public class ConcreateObserver implements Observer {     //觀察者名字    private String name;     //訂閱主題    private Subject subject;     public ConcreateObserver(String name, Subject subject) {        this.name = name;        this.subject = subject;        subject.subscribe(this);    }     //一般僅僅只是通知的時候可以換個名字,但是有業務操作的時候就建議用update    public void update(Subject subject) {        ConcreateSubject concreateSubject = (ConcreateSubject) subject;        System.out.println("observerName = " + this.name + "\n" + concreateSubject.getSubject() + " changed...." + "\n" + "status = " + Status.getStatus(concreateSubject.getStatus()).getStatusName() + "\n");    }     @Override    public String toString() {        return "ConcreateObserver{" +                "name='" + name + '\'' +                ", subject=" + subject +                '}';    }}

最後看看具體的調用:

Client:

public class Client {     public static void main(String args[]) {        //定義一個主題        ConcreateSubject subject = new ConcreateSubject("com.sankuai.sendMessage");        //定義兩個觀察者        ConcreateObserver sendObserver = new ConcreateObserver("send_message", subject);        ConcreateObserver reSendMessage = new ConcreateObserver("re_send_message", subject);        //更改訊息狀態        subject.changed(Status.SEND.status);    }}

後記 在設計觀察者模式的時候一定要注意以下幾點:
首先要明確誰是觀察者誰是被觀察者,只要明確誰是關注對象,問題也就明白了,一般觀察者與被觀察者之間是一對多的關係,一個被觀察者可以有多個觀察者,舉個例子吧,比如一個編輯框,有滑鼠點擊的觀察者,還有內容改變的觀察者,等等。 被觀察者在發送廣播通知的時候,無需指定具體的Observer,Observer可以自己決定是否要訂閱Subject的通知; 被觀察者至少需要有三個方法:添加監聽者,移除監聽者,通知觀察者;觀察者至少有一個方法:更新,更新當前的內容,並作出處理; 最後說說該模式應用情境:a.對一個對象的狀態的更新需要其他對象同步更新,或者一個對象的更新需要依賴於另外的對象更新;b.對象僅需要將自己的更新通知給其他的對象,不需要知道其他對象的細節,比如訊息推送。 推模型和拉模型:

觀察者模式根據其側重的功能還可以分為推模型和拉模型

推模型:被觀察者像向觀察者推送主題相關資訊,不管觀察者是否需要,一般這種模型的實現中,會把唄觀察者對象中的資訊通過update(Object obj)傳遞給觀察者;

拉模型:被觀察者在通知觀察者的時候,只需要傳遞少量資訊。如果觀察者需要更具體的資訊,有觀察者主動到被觀察者對象中擷取,相當於是觀察者到被觀察者對象中拉取資料。一般這種模型的視線中,會把被觀察者對象自身通過update方法傳遞給觀察者update(Subject subject),這樣在觀察者需要擷取資料的時候,就可以通過這個引用來擷取。


JDK中也支援觀察者的模式,具體源碼分析也會在後續的博文中給出。


聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.