电脑知识|欧美黑人一区二区三区|软件|欧美黑人一级爽快片淫片高清|系统|欧美黑人狂野猛交老妇|数据库|服务器|编程开发|网络运营|知识问答|技术教程文章 - 好吧啦网

您的位置:首頁技術文章
文章詳情頁

Vue Object 的變化偵測實現代碼

瀏覽:30日期:2023-01-26 17:31:59

數據觀察

Vue 中的對象變化偵測是通過Object.definePorperty實現的,但是Object.definePorperty的方式有缺陷,比如不能直接代理整個對象,每次都要循環遍歷對象的所有屬性;尤大大說之后會使用 ES6 中的Proxy 重寫這個部分。這篇博客介紹的是 Object.definePorperty 實現的對象偵測。

我們來看下面這段代碼,定義一個 defineReactive 函數,使用 Object.definePorperty 遍歷對象對象屬性的時候,設置 get 和 set;當對象屬性被讀取的時候觸發 get,對象屬性被設置的時候觸發 set。這樣就完成了對 data 的數據劫持,因為 Vue 的思想是響應式的,我們還需要收集這些變化。

function defineReactive(data,key,val){ Object.definePorperty(data,key,{ enumerable: true, configurable: true, get:function(){ return val; } set :function (newVal){ if(val === newVal){return} val = newVal; } })}

依賴 收集

創建一個 Dep 類,在 get 中收集依賴,在 set 中新增依賴

class Dep{ constructor(){ this.arr = [] } addSub(sub){ this.arr.push(sub) } removeSub(sub){ remove(this.arr,sub) } depend(){ if(window.target){ this.addSub(window.target) } } notify(){ const arrs = this.arr.slice(); for(let i = 0; i< arrs.lenth ;i ++){ arrs[i].update(); } }}function defineReactive(data,key,val){ let dep = new Dep() Object.definePorperty(data,key,{ enumerable: true, configurable: true, get:function(){ dep.depend(); // 收集依賴 return val; } set :function (newVal){ if(val === newVal){return} val = newVal; dep.notify(); // 新增依賴 } })}

Observer 和 Watcher

我們發現 defineReactive 函數只能將某一個屬性轉換為 get/set 的形式,所以我們需要一個觀察者 Observer 用來幫助遞歸的偵測所有的 key

class Observer{ constructor(value){ this.value = value } if(!Array.isArry(value)){ this.walk(value) } walk(obj){ const keys = Object.keys(obj) for(let i = 0; i < keys.length ;i++){ defineReactive(data,keys[i],obj[keys[i]) } }}

當這些依賴收集完成之后,我們要通知誰呢?怎么樣能讓視圖知道有變化更新?我們需要實現一個訂閱者 Watcher,每次觸發 get 的時候都將 dep 指向自己,這樣就可以收集到依賴;每次 set 的時候都循環調用 Watcher 的 update 方法。

class Watcher{ constructor(vm,exp,cb){ this.vm = vm; this.cb = cb; this.exp = exp; this.value = this.get(); } get(){ Dep.target = this; // 將當前訂閱者指向自己 var value = this.vm[exp]; // 觸發getter,添加自己到屬性訂閱器中 Dep.target = null; // 添加完畢,重置 return value; } update(){ const oldVal = this.value; this.value = this.get(); this.cb.call(this.vm,this.value,oldVal) }}

當 Vue 實例掛載好之后,模板都會綁定一個 Watcher,誰的屬性發生變化了就會通知響應的 Watcher,Watcher 再去通知編譯器 Compile 進行視圖更新

偵測沒辦法監聽到對象上屬性的新增和刪除

Vue 通過Object.definePorperty將對象的 key 轉化為 getter setter 的形式來進行偵測,但是無法追蹤到屬性的新增和刪除,所以 Vue 中提供了 vm.get 來實現

到此這篇關于Vue Object 的變化偵測實現代碼的文章就介紹到這了,更多相關Vue Object 變化偵測 內容請搜索好吧啦網以前的文章或繼續瀏覽下面的相關文章希望大家以后多多支持好吧啦網!

標簽: Vue
相關文章:
主站蜘蛛池模板: 高低温试验箱-模拟高低温试验箱订制-北京普桑达仪器科技有限公司【官网】 | 乳化沥青设备_改性沥青设备_沥青加温罐_德州市昊通路桥工程有限公司 | LCD3D打印机|教育|桌面|光固化|FDM3D打印机|3D打印设备-广州造维科技有限公司 | 超声骨密度仪-骨密度检测仪-经颅多普勒-tcd仪_南京科进实业有限公司 | 继电器模组-IO端子台-plc连接线-省配线模组厂家-世麦德 | 米顿罗计量泵(科普)——韬铭机械 | 会议会展活动拍摄_年会庆典演出跟拍_摄影摄像直播-艾木传媒 | AGV无人叉车_激光叉车AGV_仓储AGV小车_AGV无人搬运车-南昌IKV机器人有限公司[官网] | 元拓建材集团官方网站 | 世界箱包品牌十大排名,女包小众轻奢品牌推荐200元左右,男包十大奢侈品牌排行榜双肩,学生拉杆箱什么品牌好质量好 - Gouwu3.com | 美的商用净水器_美的直饮机_一级代理经销商_Midea租赁价格-厂家反渗透滤芯-直饮水批发品牌售后 | 荣事达手推洗地机_洗地机厂家_驾驶式扫地机_工业清洁设备 | 碳化硅,氮化硅,冰晶石,绢云母,氟化铝,白刚玉,棕刚玉,石墨,铝粉,铁粉,金属硅粉,金属铝粉,氧化铝粉,硅微粉,蓝晶石,红柱石,莫来石,粉煤灰,三聚磷酸钠,六偏磷酸钠,硫酸镁-皓泉新材料 | 耳模扫描仪-定制耳机设计软件-DLP打印机-asiga打印机-fitshape「飞特西普」 | 注塑机-压铸机-塑料注塑机-卧式注塑机-高速注塑机-单缸注塑机厂家-广东联升精密智能装备科技有限公司 | 体检车_移动CT车_CT检查车_CT车_深圳市艾克瑞电气有限公司移动CT体检车厂家-深圳市艾克瑞电气有限公司 | 最新电影-好看的电视剧大全-朝夕电影网 | 压滤机滤板_厢式_隔膜_板框压滤机滤板厂家价格型号材质-大凯环保 | 电梯乘运质量测试仪_电梯安全评估测试仪-武汉懿之刻 | 山东信蓝建设有限公司官网| 西安文都考研官网_西安考研辅导班_考研培训机构_西安在职考研培训 | 微波消解仪器_智能微波消解仪报价_高压微波消解仪厂家_那艾 | 有福网(yofus.com)洗照片冲印,毕业聚会纪念册相册制作个性DIY平台 | 购买舔盐、舔砖、矿物质盐压块机,鱼饵、鱼饲料压块机--请到杜甫机械 | 工业插头-工业插头插座【厂家】-温州罗曼电气 | 宝鸡市人民医院 | 中国在职研究生招生信息网 | 清水-铝合金-建筑模板厂家-木模板价格-铝模板生产「五棵松」品牌 | 海尔生物医疗四川代理商,海尔低温冰箱四川销售-成都壹科医疗器械有限公司 | 精密五金冲压件_深圳五金冲压厂_钣金加工厂_五金模具加工-诚瑞丰科技股份有限公司 | 钢托盘,钢制托盘,立库钢托盘,金属托盘制造商_南京飞天金属制品实业有限公司 | 塑料撕碎机_编织袋撕碎机_废纸撕碎机_生活垃圾撕碎机_废铁破碎机_河南鑫世昌机械制造有限公司 | 超声波清洗机_超声波清洗机设备_超声波清洗机厂家_鼎泰恒胜 | 多米诺-多米诺世界纪录团队-多米诺世界-多米诺团队培训-多米诺公关活动-多米诺创意广告-多米诺大型表演-多米诺专业赛事 | 江苏全风,高压风机,全风环保风机,全风环形高压风机,防爆高压风机厂家-江苏全风环保科技有限公司(官网) | 密集柜_档案密集柜_智能密集架_密集柜厂家_密集架价格-智英伟业 密集架-密集柜厂家-智能档案密集架-自动选层柜订做-河北风顺金属制品有限公司 | 加盟店-品牌招商加盟-创业项目商机平台| 噪声治理公司-噪音治理专业隔音降噪公司 | 膜片万向弹性联轴器-冲压铸造模具「沧州昌运模具」 | 合肥白癜风医院_合肥治疗白癜风医院_合肥看白癜风医院哪家好_合肥华研白癜风医院 | 浴室柜-浴室镜厂家-YINAISI · 意大利设计师品牌 | 咿耐斯 |-浙江台州市丰源卫浴有限公司 |