摘要:什么是發(fā)布訂閱模式什么是發(fā)布訂閱模式我這里不多就不多闡述了,給大家提供幾個(gè)我覺得講的比較好的博文,請各位自行閱讀發(fā)布訂閱模式解釋這一篇文章應(yīng)該是一個(gè)寫的,但是設(shè)計(jì)模式這種東西并不分語言,各位可以借鑒一下中理解發(fā)布訂閱模式這一篇是我們前
什么是發(fā)布訂閱模式
什么是發(fā)布訂閱模式我這里不多就不多闡述了,給大家提供幾個(gè)我覺得講的比較好的博文,請各位自行閱讀
發(fā)布-訂閱模式解釋 這一篇文章應(yīng)該是一個(gè)java coder寫的,但是設(shè)計(jì)模式這種東西并不分語言,各位可以借鑒一下
Javascript中理解發(fā)布--訂閱模式這一篇是我們前端人寫的,但是比較長,大家有耐心可以看看
我對發(fā)布中心的實(shí)現(xiàn),可以不看(看了能夠更好的理解發(fā)布訂閱模式)
//實(shí)現(xiàn)發(fā)布中心 /* * log=[{ * index: Number, 日志編號(hào)(自增) * type: String, 日志類型("subscribe","unsubscribe","publish") * eventName: String, 事件名 * time: new Date(), 時(shí)間 * fun:Function 訂閱/取訂的方法(只有日志類型為"subscribe"或"unsubscribe"的才有) * param:Object 觸發(fā)事件時(shí)的參數(shù)(只有日志類型為"publish"的才有) * }] * eventCenter = { * eventName:[Function,Function] //eventName即為事件名,其值為訂閱方法列表 * } * .subscribe(eventName, fun) 訂閱 eventName:事件名 fun:訂閱方法 * .unsubscribe(eventName, fun) 取訂 eventName:事件名 fun:訂閱方法 * .publish(eventName[,param]) 發(fā)布 eventName:事件名 param:事件參數(shù) * .showLog([filter]) 日志展示 filter 過濾器,同數(shù)組的過濾器用法 返回過濾后的log * .showEventCenter([eventName]) 事件中心 eventName 事件名 返回事件綁定的方法 * */ let subscribeCenter = function () { //事件中心 let eventCenter = {}; //日志 let log = []; //添加日志函數(shù) function pushLog(type, eventName, fun, param) { let info = { index: log.length, type: type, eventName: eventName, time: new Date() }; if (fun) { info.fun = fun; } if (param) { info.param = param; } log.push(info) } return { //訂閱 subscribe(eventName, fun) { pushLog("subscribe", eventName, fun); eventCenter[eventName] = eventCenter[eventName] || []; eventCenter[eventName].push(fun); }, //取消訂閱 unsubscribe(eventName, fun) { pushLog("unsubscribe", eventName, fun); let onList = eventCenter[eventName]; if (onList) { for (let i = 0; i < onList.length; i++) { if (onList[i] === fun) { onList.splice(i, 1); return } } } }, //發(fā)布 publish(eventName, param) { pushLog("publish", eventName, null, param) let onList = eventCenter[eventName]; if (onList) { for (let i = 0; i < onList.length; i++) { onList[i](param) } } }, //顯示日志 showLog(filter) { filter = filter || (() => true); let returnLog = log.filter(filter); returnLog.forEach(x => { let y = {}; for (let key in x) { y[key] = x[key] } return y }); return returnLog; }, //顯示事件中心 showEventCenter(eventName) { let selectEM = eventName ? eventCenter[eventName] : eventCenter, returnEM = {}; for (let key in selectEM) { returnEM[key] = []; selectEM[key].forEach(x => { returnEM[key].push(x) }); } return returnEM } } }();
如果有看我上一篇文章中事件監(jiān)聽實(shí)現(xiàn)的朋友應(yīng)該對這個(gè)不部分代碼有一種熟悉的感覺,確實(shí)事件監(jiān)聽和發(fā)布訂閱的實(shí)現(xiàn)非常的像。我主要多做的就是一個(gè)日志的拓展,保證了每次的動(dòng)作都可以被監(jiān)聽和查看;
發(fā)布中心API這個(gè)在上面是有的,但是因?yàn)樯厦娴牟糠钟幸恍┩瑢W(xué)是不看的,所以就在這里摘出來,方便這些同學(xué)了解發(fā)布中心的用法
/* * log=[{ * index: Number, 日志編號(hào)(自增) * type: String, 日志類型("subscribe","unsubscribe","publish") * eventName: String, 事件名 * time: new Date(), 時(shí)間 * fun:Function 訂閱/取訂的方法(只有日志類型為"subscribe"或"unsubscribe"的才有) * param:Object 觸發(fā)事件時(shí)的參數(shù)(只有日志類型為"publish"的才有) * }] * eventCenter = { * eventName:[Function,Function] //eventName即為事件名,其值為訂閱方法列表 * } * .subscribe(eventName, fun) 訂閱 eventName:事件名 fun:訂閱方法 * .unsubscribe(eventName, fun) 取訂 eventName:事件名 fun:訂閱方法 * .publish(eventName[,param]) 發(fā)布 eventName:事件名 param:事件參數(shù) * .showLog([filter]) 日志展示 filter 過濾器,同數(shù)組的過濾器用法 返回過濾后的log * .showEventCenter([eventName]) 事件中心 eventName 事件名 返回事件綁定的方法 * */發(fā)布/訂閱模式在異步中的應(yīng)用
這里是重點(diǎn),需要大家仔細(xì)看,理解了這段代碼不光可以解決異步問題,還可以理解發(fā)布訂閱者模式是如何應(yīng)用的;
//發(fā)布者 let f1 = function () { setTimeout(function () { console.log(""done" 事件發(fā)布 參數(shù):", 123); subscribeCenter.publish("done", 123); console.log("事件中心", subscribeCenter.showEventCenter()); console.log("f3 取訂 "done""); subscribeCenter.unsubscribe("done", f3); setTimeout(function () { console.log(""done" 事件發(fā)布 參數(shù):", 233); subscribeCenter.publish("done", 233); console.log("事件中心", subscribeCenter.showEventCenter()); console.log("日志", subscribeCenter.showLog()); }, 100) }, 100) }; //訂閱者 let f2 = function (param) { console.log("f2 is running, param is", param); }; //訂閱者 let f3 = function (param) { console.log("f3 is running, param is", param) }; //訂閱 console.log("f2 訂閱 "done""); subscribeCenter.subscribe("done", f2); console.log("f3 訂閱 "done""); subscribeCenter.subscribe("done", f3); //發(fā)布 f1();
先貼運(yùn)行結(jié)果
在這里可以看到,該模式與事件監(jiān)聽模式非常相似,但是所有的發(fā)布都通過了同一個(gè)發(fā)布中心來控制,這樣的話可以方便我們追蹤整個(gè)事件的狀態(tài);
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://specialneedsforspecialkids.com/yun/103268.html
摘要:概念觀察者模式被廣泛地應(yīng)用于客戶端編程中。所有的瀏覽器事件,等都是使用觀察者模式的例子。在觀察者模式中,一個(gè)對象訂閱另一個(gè)對象的指定活動(dòng)并得到通知,而不是調(diào)用另一個(gè)對象的方法。此外,觀察者模式還可用于實(shí)現(xiàn)數(shù)據(jù)綁定。 概念 觀察者模式被廣泛地應(yīng)用于JavaScript客戶端編程中。所有的瀏覽器事件(mouseover,keypress等)都是使用觀察者模式的例子。這種模式的另一個(gè)名字叫自...
摘要:應(yīng)用需要正確并合適響應(yīng)各種網(wǎng)絡(luò)請求用戶操作計(jì)時(shí)事件和各種延時(shí)動(dòng)作。好了,我們的新流程圖畫出來了提示城市名稱查找不是很復(fù)雜,谷歌地圖為此提供了非常簡單的。形象點(diǎn)表示就是,函數(shù)是一等公民。 By Hubert Zub | Oct 3, 2018 原文 當(dāng)你將關(guān)注點(diǎn)從樣式,美學(xué)和網(wǎng)格系統(tǒng)轉(zhuǎn)移到邏輯,框架和編寫JavaScript代碼時(shí)。一切都開始了,你會(huì)發(fā)現(xiàn)你處于你的web開發(fā)歷程中最激動(dòng)人...
摘要:微內(nèi)核架構(gòu)在大型前端系統(tǒng)中的應(yīng)用只討論架構(gòu),不討論框架名詞解釋由一群盡可能將數(shù)量最小化的軟件程序組成,他們負(fù)責(zé)提供實(shí)現(xiàn)一個(gè)操作系統(tǒng)所需要的各種機(jī)制和功能。而微內(nèi)核架構(gòu)已經(jīng)在操作系統(tǒng)和很多的產(chǎn)品的后端服務(wù)及前端中經(jīng)過了很多的實(shí)踐。 微內(nèi)核架構(gòu)在大型前端系統(tǒng)中的應(yīng)用 只討論架構(gòu),不討論框架 1、名詞解釋 由一群盡可能將數(shù)量最小化的軟件程序組成,他們負(fù)責(zé)提供、實(shí)現(xiàn)一個(gè)操作系統(tǒng)所需要的各種機(jī)制...
摘要:小程序很多方法都是異步的原因官方說法天生異步剛接觸小程序的時(shí)候,發(fā)現(xiàn)很多微信提供的都是異步的,如路由跳轉(zhuǎn),設(shè)置和讀取緩存,還有獲取節(jié)點(diǎn)信息等微信的,都是異步的,需要傳入回調(diào)函數(shù)才能獲得結(jié)果,在我們正常的前端開發(fā)中,這些都不是異步的,當(dāng)時(shí)很奇 1. 小程序很多方法都是異步的原因(官方說法:天生異步) 剛接觸小程序的時(shí)候,發(fā)現(xiàn)很多微信提供的api都是異步的,如路由跳轉(zhuǎn),設(shè)置和讀取緩存,還有...
閱讀 632·2021-08-17 10:15
閱讀 1715·2021-07-30 14:57
閱讀 1971·2019-08-30 15:55
閱讀 2813·2019-08-30 15:55
閱讀 2704·2019-08-30 15:44
閱讀 662·2019-08-30 14:13
閱讀 2380·2019-08-30 13:55
閱讀 2588·2019-08-26 13:56