国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 語言 > JavaScript > 正文

Vue監聽數據對象變化源碼

2024-05-06 15:10:01
字體:
來源:轉載
供稿:網友

監聽數據對象變化,最容易想到的是建立一個需要監視對象的表,定時掃描其值,有變化,則執行相應操作,不過這種實現方式,性能是個問題,如果需要監視的數據量大的話,每掃描一次全部的對象,需要的時間很長。當然,有些框架是采用的這種方式,不過他們用非常巧妙的算法提升性能,這不在我們的討論范圍之類。

Vue 中數據對象的監視,是通過設置 ES5 的新特性(ES7 都快出來了,ES5 的東西倒也真稱不得新)Object.defineProperty() 中的 set、get 來實現的。

目標

與官方文檔第一個例子相似,不過也有簡化,因為這篇只是介紹下數據對象的監聽,不涉及文本解析,所以文本解析相關的直接舍棄了:

<div id="app"></div>var app = new Vue({ el: 'app', data: { message: 'Hello Vue!' }});

瀏覽器顯示:

Hello Vue!

在控制臺輸入諸如:

app.message = 'Changed!'

之類的命令,瀏覽器顯示內容會跟著修改。

Object.defineProperty

引用 MDN 上的定義:

Object.defineProperty()方法會直接在一個對象上定義一個新屬性,或者修改一個已經存在的屬性, 并返回這個對象。
與此相生相伴的還有一個 Object.getOwnPropertyDescriptor():

Object.getOwnPropertyDescriptor() 返回指定對象上一個自有屬性對應的屬性描述符。(自有屬性指的是直接賦予該對象的屬性,不需要從原型鏈上進行查找的屬性)

下面的例子用一種比較簡單、直觀的方式來設置 setter、getter:

var dep = [];function defineReactive(obj, key, val) { // 有自定義的 property,則用自定義的 property var property = Object.getOwnPropertyDescriptor(obj, key); if(property && property.configurable === false) { return; } var getter = property && property.get; var setter = property && property.set; Object.defineProperty(obj, key, { enumerable: true, configurable: true, get: function() {  var value = getter ? getter.call(obj) : val;  dep.push(value);  return value; }, set: function(newVal) {  var value = getter ? getter.call(obj) : val;  // set 值與原值相同,則不更新  if(newVal === value) {  return;  }  if(setter) {  setter.call(obj, newVal);  } else {  val = newVal;  }  console.log(dep); } });}
var a = {};defineReactive(a, 'a', 12);// 調用 getter,12 被壓入 dep,此時 dep 值為 [12]a.a;// 調用 setter,輸出 dep ([12])a.a = 24;// 調用 getter,24 被壓入 dep,此時 dep 值為 [12, 24]a.a;

Observer

簡單說過 Object.defineProperty 之后,就要開始扯 Observer 了。observer,中文解釋為“觀察者”,觀察什么東西呢?觀察對象屬性值的變化。故此,所謂 observer,就是給對象的所有屬性加上 getter、setter,如果對象的屬性還有屬性,比如說 {a: {a: {a: 'a'}}},則通過遞歸給其屬性的屬性也加上 getter、setter:

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表

圖片精選

主站蜘蛛池模板: 海安县| 平凉市| 崇左市| 佳木斯市| 白城市| 岗巴县| 左贡县| 美姑县| 松桃| 永康市| 沙坪坝区| 焦作市| 商洛市| 广平县| 曲麻莱县| 无锡市| 奎屯市| 潼关县| 红安县| 资溪县| 青冈县| 南江县| 绥化市| 牟定县| 汾阳市| 萝北县| 淮阳县| 德阳市| 旅游| 济宁市| 中江县| 临沂市| 泰兴市| 原平市| 湾仔区| 环江| 阳山县| 家居| 响水县| 鄂托克旗| 北流市|