一. 前言
我在spring篇,介紹過ApplicationListener,接收到spring的一些事件,就會觸發(fā)相應的通知操作。這是典型的發(fā)布訂閱模式,也就是觀察者模式。
說到發(fā)布訂閱,大家還會想到MQ,Zookeeper等,這些很許多事件監(jiān)聽,也是觀察者模式的一種體現(xiàn)。
本文中,我們來討論下如何實現(xiàn)這一模式。
二. 模型抽象
2.1 觀察者模式的主要角色
- 抽象主題(Subject)角色:也叫抽象目標類,它提供了一個用于保存觀察者對象的聚集類和增加、刪除觀察者對象的方法,以及通知所有觀察者的抽象方法。
- 具體主題(Concrete Subject)角色:也叫具體目標類,它實現(xiàn)抽象目標中的通知方法,當具體主題的內部狀態(tài)發(fā)生改變時,通知所有注冊過的觀察者對象。
- 抽象觀察者(Observer)角色:它是一個抽象類或接口,它包含了一個更新自己的抽象方法,當接到具體主題的更改通知時被調用。
- 具體觀察者(Concrete Observer)角色:實現(xiàn)抽象觀察者中定義的抽象方法,以便在得到目標的更改通知時更新自身的狀態(tài)。
2.2 結構模型抽象

觀察者模式的結構圖
2.3 代碼實現(xiàn)
- 主題抽象
public interface Subject {
// 添加訂閱關系
void attach(Observer observer);
// 移除訂閱關系
void detach(Observer observer);
// 通知訂閱者
void notifyObservers(String message);
}
- 具象實現(xiàn)
也就是具體事件的訂閱與通知
public class ConcreteSubject implements Subject {
// 訂閱者容器
private List<Observer> observers = new ArrayList<Observer>();
/**
* 增加觀察者
*
* @param observer
*/
@Override
public void attach(Observer observer) {
observers.add(observer);
}
@Override
public void detach(Observer observer) {
observers.remove(observer);
}
@Override
public void notifyObservers(String message) {
// 通知訂閱者們
for (Observer observer : observers) {
observer.response(message);
}
}
}
- 觀察者抽象
public interface Observer {
// 接收推送消息,處理業(yè)務邏輯
void response(String message);
}
- 具體訂閱者處理通知
public class ConcreteObserver implements Observer {
@Override
public void response(String message) {
//接收到主題推送消息,做具體業(yè)務處理
System.out.println("具體的觀察者收到了具體主題推送的消息: " + message);
}
}
至此,我們就有了發(fā)布訂閱模型,該模式重點是抽象,也就是面向接口編程,實現(xiàn)了業(yè)務的解耦。