javascript
再起航,我的学习笔记之JavaScript设计模式23(中介者模式)
中介者模式
概念介紹
中介者模式(Mediator):通過中介者對(duì)象封裝一系列對(duì)象之間的交互,使對(duì)象之間不再相互引用降低他們之間的耦合,有時(shí)中介者對(duì)象也可以改變對(duì)象之間的交互。
創(chuàng)建一個(gè)中介
中介者模式,從生活的角度上來講,和我們賣房子的中介很像,比如我有一套房想要出租,而你又想要租房子,那么我們就可以通過中介達(dá)成交易,我不考慮租給了歲,租房者也不用考慮租了誰的房子,因?yàn)橛兄薪樵谒燥@得很方便。
從代碼的角度講,如果有多個(gè)類或多個(gè)子系統(tǒng)相互交互,而且交互很繁瑣,導(dǎo)致每個(gè)類都必須知道他需要交互的類,這樣它們的耦合會(huì)顯得異常厲害,如果這個(gè)時(shí)候我們需要處理某一個(gè)類,那很可能就要陷入無盡的調(diào)試中了。
那么這個(gè)時(shí)候我們就可以用到中介者模式,我們把對(duì)象全都交給中介者對(duì)象,然后通過中介者對(duì)象處理這些復(fù)雜的關(guān)系。
下面我們模擬一下房東找中介發(fā)布消息,租戶找中介接收消息吧:
//中介者對(duì)象 var Mediator=function(){//消息對(duì)象var _msg={};return{//訂閱方法register:function(type,action){//如果存在該消息if(_msg[type]){//存入回調(diào)函數(shù)_msg[type].push(action);}else{//不存在我們建立消息容器_msg[type]=[];//存入新消息回調(diào)函數(shù)_msg[type].push(action);}},//發(fā)布方法send:function(type){//如果該消息被訂閱if(_msg[type]){//遍歷存儲(chǔ)的消息回調(diào)函數(shù)for (var i=0;i<_msg[type].length;i++) {_msg[type][i]&&_msg[type][i]();}}}} }();我們的中介對(duì)象創(chuàng)建成功了下面我們來測試一下
Mediator.register('landlord',function(){console.log('房東發(fā)布第一條消息'); }); Mediator.register('landlord',function(){console.log('房東發(fā)布第二條消息'); }) Mediator.register('tenant',function(){console.log('租戶接收第一條消息'); }); Mediator.register('tenant',function(){console.log('租戶接收第二條消息'); }) Mediator.send('landlord');Mediator.send('tenant');現(xiàn)在我們的中介者模式成功了。
利用中介者模式實(shí)現(xiàn)商品購買
我們現(xiàn)在在編寫一個(gè)商品購買的頁面,在購買流程中,可以選擇商品及樣式輸入購買的數(shù)量,同時(shí)頁面中有兩個(gè)展示區(qū)域,分別向用戶展示剛剛選擇的商品、種類與數(shù)量。還有一個(gè)按鈕動(dòng)態(tài)顯示下一步的操作,我們查詢商品對(duì)應(yīng)的庫存,如果庫存數(shù)量少于這次的購買數(shù)量,按鈕將被禁止且顯示庫存不足,反之按鈕可以點(diǎn)擊并且顯示放入購買車
頁面元素如下:
<select id="shoesBrands"> <option>請(qǐng)選擇</option> <option>Adidas</option> <option>Nike</option> </select> <select id="shoesType"> <option>請(qǐng)選擇</option> <option>運(yùn)動(dòng)鞋</option> <option>球鞋</option> </select> <input type="text" id="numberInput" /> <p id="shoesInfo"></p> <p id="typeInfo"></p> <p id="numberInfo"></p> <button id="nextBtn">下一步</button>接著我們開始寫實(shí)現(xiàn)方法
//創(chuàng)建一個(gè)商品對(duì)象記錄庫存var goods = { "Adidas|運(yùn)動(dòng)鞋": 23, "Adidas|球鞋": 35, "Nike|運(yùn)動(dòng)鞋": 0, "Nike|球鞋": 2 }; //創(chuàng)建中介者對(duì)象var mediator = ( function(){ var shoesBrands = document.getElementById( "shoesBrands" ), shoesType = document.getElementById( "shoesType" ), numberInput = document.getElementById( "numberInput" ), shoesInfo = document.getElementById( "shoesInfo" ), typeInfo = document.getElementById( "typeInfo" ), numberInfo = document.getElementById( "numberInfo" ), nextBtn = document.getElementById( "nextBtn" ); return { //當(dāng)選項(xiàng)發(fā)生改變時(shí)觸發(fā)下面方法change: function( obj ){ var shoes = shoesBrands.value, //品牌 type = shoesType.value, //類型number = numberInput.value, //數(shù)量 stock = goods[ shoes + "|" + type ]; //品牌類型下鞋子對(duì)應(yīng)庫存數(shù)量 if( obj === shoesBrands ){ shoesInfo.innerHTML = shoes; }else if( obj === shoesType ){ typeInfo.innerHTML = type; }else if( obj === numberInput ){ numberInfo.innerHTML = number; } if( !shoes ){ nextBtn.disabled = true; shoesInfo.innerHTML = "請(qǐng)選擇鞋的品牌"; return; } if( !type ){ nextBtn.disabled = true; typeInfo.innerHTML = "請(qǐng)選擇鞋的類型"; return; } if( !(Number.isInteger( number - 0 ) && number > 0) ){ //輸入購買數(shù)量是否為正整數(shù) nextBtn.disabled = true; numberInfo.innerHTML = "請(qǐng)輸入正確的購買數(shù)量"; return; } if(number>stock){nextBtn.disabled = true; nextBtn.innerHTML = "庫存不足"; }else{nextBtn.disabled = false; nextBtn.innerHTML = "放入購物車"; }} } } )();我們調(diào)用看看
shoesBrands.onchange = function(){ mediator.change( this ); }; shoesType.onchange = function(){ mediator.change( this ); }; numberInput.onchange = function(){ mediator.change( this ); }總結(jié)
同觀察者模式一樣,中介者模式的主要業(yè)務(wù)也是通過模塊間或者對(duì)象間的復(fù)雜通信,來解決模塊間或?qū)ο箝g的耦合,對(duì)于中介者對(duì)象的本質(zhì)是封裝多個(gè)對(duì)象的交互,并且這些交互一般都是在中介者內(nèi)部實(shí)現(xiàn)的。
與外觀模式的封裝特性相比
中介者模式對(duì)多個(gè)對(duì)象交互地封裝,且這些對(duì)象一般處于同一層面上,并且封裝的交互在中介者內(nèi)部,而外觀模式的封裝是為了提供更簡單的醫(yī)用的接口而不會(huì)添加其他功能
與觀察者模式相比
雖然兩種模式都是通過消息傳遞實(shí)現(xiàn)對(duì)象間或模塊間的解耦。觀察者模式中的訂閱者是雙向的,既可以是消息的發(fā)布者,也可以是消息的訂閱者。而在中介者模式中,訂閱者是單向的,只能是消息的訂閱者, 而消息統(tǒng)一由中介者對(duì)象發(fā)布,所有的訂閱者對(duì)象間接地被中介者管理
也謝謝大家看到這里:)如果你覺得我的分享還可以請(qǐng)點(diǎn)擊推薦,分享給你的朋友讓我們一起進(jìn)步~
好了以上就是本次分享的全部內(nèi)容,本次示例參考自JavaScript設(shè)計(jì)模式一書,讓我們一點(diǎn)點(diǎn)積累一點(diǎn)點(diǎn)成長,希望對(duì)大家有所幫助。
歡迎轉(zhuǎn)載,轉(zhuǎn)載請(qǐng)注明作者,原文出處。
轉(zhuǎn)載于:https://www.cnblogs.com/chen-jie/p/JavaScript-Mediator.html
總結(jié)
以上是生活随笔為你收集整理的再起航,我的学习笔记之JavaScript设计模式23(中介者模式)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: java技术系列(一) Enum
- 下一篇: JavaScript高级程序设计之基本概