javscript-發布訂閱模式與觀察者模式
阿新 • • 發佈:2019-03-10
splice reac 解決方法 狀態 square n) 方法 vsc 模式
設計模式”(Design Pattern)是針對編程中經常出現的、具有共性的問題,所提出的解決方法。著名的《設計模式》一書一共提出了23種模式。
發布訂閱模式
它定義了一種對象間一對多的關系,多個訂閱者對象將自己的“主題/事件”註冊進一個目標對象,當目標對象狀態發生改變時,只需要去執行對應訂閱者註冊的 "主題/事件" 就行了。這是一種松耦合的狀態。目標對象不用關心任何訂閱者的情況, 只需要發布註冊在自己身上的事件就行了。
訂閱者只管註冊 目標對象只管發布 互不影響
代碼實現:
let event = { clientList: {}, listen (key, fn) { if (!this.clientList[key]) { this.clientList[key] = [] } this.clientList[key].push(fn) // 訂閱的消息添加進緩存列表 }, trigger (type, money) { let fns = this.clientList[type] if (!fns || fns.length === 0) { // 如果沒有綁定對應的消息 return false } fns.forEach(fn => { fn.apply(this, [money]) }) } } // 再定義一個installEvent函數,用於給所有對象動態安裝發布-訂閱功能 // 如:另一家售樓處也想要這個功能,就可以調用這個註冊了,不用再寫多一次這段代碼 let installEvent = obj => { for (let i in event) { obj[i] = event[i] } } // 給售樓處對象salesOffices動態增加發布-訂閱功能 let salesOffices = {} installEvent(salesOffices) // 小明訂閱信息 salesOffices.listen('squareMeter88', price => { console.log('小明,你看中的88平方的房子,價格=' + price) }) // 小光訂閱信息 salesOffices.listen('squareMeter88', price => { console.log('小光,你看中的88平方的房子,價格=' + price) }) // 小紅訂閱信息 salesOffices.listen('squareMeter100', price => { console.log('小紅,你看中的100平方的房子,價格=' + price) }) salesOffices.trigger('squareMeter88', 2000000) salesOffices.trigger('squareMeter100', 2500000)
觀察者模式
觀察者模式與發布訂閱最大的區別是訂閱者註冊的是自己本身,不再是註冊 “主題/事件”,當目標對象狀態發生改變時,會調用自身的通知方法,從而調用註冊在自身的訂閱者的更新方法。
//觀察者列表 function ObserverList(){ this.observerList = []; } ObserverList.prototype.add = function( obj ){ return this.observerList.push( obj ); }; ObserverList.prototype.count = function(){ return this.observerList.length; }; ObserverList.prototype.get = function( index ){ if( index > -1 && index < this.observerList.length ){ return this.observerList[ index ]; } }; ObserverList.prototype.indexOf = function( obj, startIndex ){ var i = startIndex; while( i < this.observerList.length ){ if( this.observerList[i] === obj ){ return i; } i++; } return -1; }; ObserverList.prototype.removeAt = function( index ){ this.observerList.splice( index, 1 ); }; //目標 function Subject(){ this.observers = new ObserverList(); } Subject.prototype.addObserver = function( observer ){ this.observers.add( observer ); }; Subject.prototype.removeObserver = function( observer ){ this.observers.removeAt( this.observers.indexOf( observer, 0 ) ); }; Subject.prototype.notify = function( context ){ var observerCount = this.observers.count(); for(var i=0; i < observerCount; i++){ this.observers.get(i).update( context ); } }; //觀察者 function Observer(){ this.update = function(){ // ... }; }
區別:
發布訂閱模式實現了更細粒度化的管理,觀察者模式當目標對象狀態變化時會通知所有訂閱者,而發布訂閱則會通過調度中心執行具體的訂閱者註冊的 "主題/事件",發布訂閱更松耦合一些。
javscript-發布訂閱模式與觀察者模式