当前位置: 首页 > Web前端 > vue.js

从0开始通过touch实现Vue精简版---(数组劫持)

时间:2023-04-01 01:57:42 vue.js

接上一篇:从0开始通过touch实现Vue精简版---(对象劫持)1.数组的劫持之前已经完成了对data数据中对象的native方法的劫持,但是Object.defineProperty并不能很好的支持数组的变化,所以在Vue中,采用了劫持数组native方法的操作来保证数据可以被调用正常监控。由于原方法不能正常劫持数组的数据,我们需要区分data的数据类型,所以需要重写Observer类:classObserver{constructor(data){//data===vm._data//willUser的数据使用Object.defineProperty重新定义if(Array.isArray(data)){//劫持数组方法,让数组通过链找到我们自己重写的原型方法data.__proto__=arrayMethods;}否则{这个。步行(数据);}}//...}通过使用data.__proto__将数组上的方法替换为我们重写的原型方法arrayMethods,我们创建一个新的array.js来重写我们的数组方法。/***拦截用户调用的push,shift,unshift,pop,reverse,sort,splice数组方法*///获取旧数组方法letoldArrayProtoMethods=Array.prototype;//复制新对象找到旧的一种方法,不修改原型导出上的方法];methods.forEach(method=>{arrayMethods[method]=function(...args){//函数劫持letresult=oldArrayProtoMethods[method].apply(this,args);console.log('调用数组更新方法');返回结果;}});这时候我们调用vm.arr.push(1,2,3),会打印调用数组update方法,说明此时的push方法就是我们调用的重写的方法。2.监听数组中的新对象如果我们调用vm.arr.push({a:1}),我们还需要监听数组中新的对象属性,也就是我们需要添加observe观察,所以进一步重写需要数组方法:/***劫持数组的新元素*@param{*}inserted*/+exportfunctionobserverArray(inserted){+for(leti=0;i{arrayMethods[method]=function(...args){//functionhijackletresult=oldArrayProtoMethods[method].apply(this,args);console.log('调用数组更新方法');+letinserted;+switch(method){+case'push':+case'unshift':+inserted=args;+break;+case'splice':+inserted=args.slice(2);//获取splice的新内容(start,deleteCount,[])+default:+break;+}+if(inserted)observerArray(inserted);returnresult;}});3、这样一来,如果我们在数组中添加一个对象,修改对象的值,就可以正常监听了:console.log(vm.arr.push({a:1}));console.log(vm.arr[3].a=100);这时候浏览器会打印:我们的数组劫持也已经实现了。在接下来的部分中,我们将实现如何通过模板替换数据到页面并同步更改。代码部分可以在这个提交中看到。希望大家点个star,谢谢啦~