Vue變速不變聲是指當(dāng)你改變Vue中的數(shù)據(jù)時,Vue會自動將UI更新,但是不會影響到其他的自定義事件或操作。這種特性的實現(xiàn)主要是通過Vue的響應(yīng)式系統(tǒng)。
Vue的響應(yīng)式系統(tǒng)是從vue.js初始化時就建立的,將數(shù)據(jù)中的每個屬性都轉(zhuǎn)化為getter/setter并在修改值時觸發(fā)依賴。當(dāng)一個Vue實例被創(chuàng)建時,會對所有的屬性對象進(jìn)行遞歸遍歷,使用Object.defineProperty在每個屬性上添加getter/setter方法。
var obj = { foo: 'bar' } Object.defineProperty(obj, 'foo', { get: function () { console.log('get foo') return 'bar' }, set: function (val) { console.log('set foo as ' + val) } })
當(dāng)修改obj.foo時,set函數(shù)會被觸發(fā),并在控制臺上輸出"set foo as"。而當(dāng)獲取(obj.foo)時,get函數(shù)會被觸發(fā),并在控制臺輸出"get foo"。
在Vue的響應(yīng)式系統(tǒng)中,每個組件實例都有相應(yīng)的watcher實例對象。當(dāng)數(shù)據(jù)改變時,它會通知watcher對象,隨后watcher對象會通知Vue去更新相關(guān)組件的視圖。
var watcher = new Watcher(vm, function () { vm._update(vm._render(), hydrating) }, noop, null, true /* isRenderWatcher */)
從上面的代碼可以看到,Watcher對象接收一個函數(shù)參數(shù),函數(shù)中包含Vue更新UI的代碼。當(dāng)數(shù)據(jù)發(fā)生變化時,該函數(shù)會被執(zhí)行。
當(dāng)你給Vue的data中任何一個屬性賦值時,Vue都會自動將這個屬性轉(zhuǎn)化為響應(yīng)式數(shù)據(jù)。當(dāng)數(shù)據(jù)改變時,Vue就可以監(jiān)聽到這個變化,然后通知watcher去更新對應(yīng)的UI。
var app = new Vue({ el: '#app', data: { message: 'Hello Vue!' } }) app.message = 'Hello World!'
在上面的代碼中,當(dāng)將message屬性修改為'Hello World!'時,Vue會觸發(fā)更新對應(yīng)的UI,但是不會影響任何其他操作而產(chǎn)生副作用。這也就是Vue變速不變聲的實現(xiàn)原理。
在使用Vue開發(fā)項目時,應(yīng)該盡量避免直接操作DOM,而是通過改變Vue實例中的數(shù)據(jù)來實現(xiàn)UI的更新。這樣可以確保UI的可維護(hù)性以及提高開發(fā)效率。
總結(jié)一下,Vue變速不變聲是指當(dāng)你改變Vue中的數(shù)據(jù)時,Vue會自動將UI更新,但是不會影響到其他的自定義事件或操作。這是通過Vue響應(yīng)式系統(tǒng)實現(xiàn)的,它將所有屬性轉(zhuǎn)化為getter/setter,并在每次修改數(shù)據(jù)時通知watcher對象去更新對應(yīng)的UI。在開發(fā)Vue項目時,應(yīng)該盡量避免直接操作DOM,而是通過改變Vue實例中的數(shù)據(jù)來實現(xiàn)UI的更新。