Vue的響應(yīng)式系統(tǒng)
茶陵ssl適用于網(wǎng)站、小程序/APP、API接口等需要進(jìn)行數(shù)據(jù)傳輸應(yīng)用場景,ssl證書未來市場廣闊!成為成都創(chuàng)新互聯(lián)的ssl證書銷售渠道,可以享受市場價格4-6折優(yōu)惠!如果有意向歡迎電話聯(lián)系或者加微信:13518219792(備注:SSL證書合作)期待與您的合作!Vue 最獨(dú)特的特性之一,是其非侵入性的響應(yīng)式系統(tǒng)。數(shù)據(jù)模型僅僅是普通的JavaScript 對象,而當(dāng)你修改它們時,視圖會進(jìn)行更新,這使得狀態(tài)管理非常簡單直接,我們可以只關(guān)注數(shù)據(jù)本身,而不用手動處理數(shù)據(jù)到視圖的渲染,避免了繁瑣的 DOM 操作,提高了開發(fā)效率。
vue 的響應(yīng)式系統(tǒng)依賴于三個重要的類:Dep 類、Watcher 類、Observer 類,然后使用發(fā)布訂閱模式的思想將他們?nèi)嗪显谝黄穑ú涣私獍l(fā)布訂閱模式的可以看我之前的文章發(fā)布訂閱模式與觀察者模式)。
Observer
Observe扮演的角色是發(fā)布者,他的主要作用是調(diào)用defineReactive函數(shù),在defineReactive函數(shù)中使用Object.defineProperty 方法對對象的每一個子屬性進(jìn)行數(shù)據(jù)劫持/監(jiān)聽。
部分代碼展示
defineReactive函數(shù),Observe的核心,劫持?jǐn)?shù)據(jù),在setter中向Dep(調(diào)度中心)添加觀察者,在getter中通知觀察者更新。
function defineReactive(obj, key, val, customSetter, shallow){ //監(jiān)聽屬性key //關(guān)鍵點(diǎn):在閉包中聲明一個Dep實(shí)例,用于保存watcher實(shí)例 var dep = new Dep(); var getter = property && property.get; var setter = property && property.set; if(!getter && arguments.length === 2) { val = obj[key]; } //執(zhí)行observe,監(jiān)聽屬性key所代表的值val的子屬性 var childOb = observe(val); Object.defineProperty(obj, key, { enumerable: true, configurable: true, get: function reactiveGetter() { //獲取值 var value = getter ? getter.call(obj) : val; //依賴收集:如果當(dāng)前有活動的Dep.target(觀察者--watcher實(shí)例) if(Dep.target) { //將dep放進(jìn)當(dāng)前觀察者的deps中,同時,將該觀察者放入dep中,等待變更通知 dep.depend(); if(childOb) { //為子屬性進(jìn)行依賴收集 //其實(shí)就是將同一個watcher觀察者實(shí)例放進(jìn)了兩個dep中 //一個是正在本身閉包中的dep,另一個是子屬性的dep childOb.dep.depend(); } } return value }, set: function reactiveSetter(newVal) { //獲取value var value = getter ? getter.call(obj) : val; if(newVal === value || (newVal !== newVal && value !== value)) { return } if(setter) { setter.call(obj, newVal); } else { val = newVal; } //新的值需要重新進(jìn)行observe,保證數(shù)據(jù)響應(yīng)式 childOb = observe(newVal); //關(guān)鍵點(diǎn):遍歷dep.subs,通知所有的觀察者 dep.notify(); } }); }