Review of Vue2 responsive principles// 1. Object responsiveness: traverse each key and define getter and setter // 2. Array responsiveness: Override array prototype method and add additional notification logic const originalProto = Array.prototype const arrayProto = Object.create(originalProto) ;['push', 'pop', 'shift', 'unshift', 'splice', 'reverse', 'sort'].forEach( method => { arrayProto[method] = function () { originalProto[method].apply(this, arguments) notifyUpdate() } } ) function observe(obj) { if (typeof obj !== 'object' || obj == null) { return } // Add array type judgment, if it is an array, overwrite its prototype if (Array.isArray(obj)) { Object.setPrototypeOf(obj, arrayProto) } else { const keys = Object.keys(obj) for (let i = 0; i < keys.length; i++) { const key = keys[i] defineReactive(obj, key, obj[key]) } } } function defineReactive (obj, key, val) { observe(val) // Solve the nested object problem Object.defineProperty(obj, key, { get () { return val }, set (newVal) { if (newVal !== val) { observe(newVal) // New value is an object val = newVal notifyUpdate() } } }) } function notifyUpdate () { console.log('Page updated!') }
Analysis of Vue3 responsive principleVue3 uses the Proxy feature of ES6 to solve these problems. function reactive(obj) { if (typeof obj !== 'object' && obj != null) { return obj } // Proxy is equivalent to adding interception to the outer layer of the object // http://es6.ruanyifeng.com/#docs/proxy const observed = new Proxy(obj, { get (target, key, receiver) { // Reflect is used to perform default operations on objects, which is more standardized and friendly. // Proxy and Object methods have corresponding Reflect methods. // http://es6.ruanyifeng.com/#docs/reflect const res = Reflect.get(target, key, receiver) console.log(`Get ${key}:${res}`) return res }, set (target, key, value, receiver) { const res = Reflect.set(target, key, value, receiver) console.log(`Set ${key}:${value}`) return res }, deleteProperty (target, key) { const res = Reflect.deleteProperty(target, key) console.log(`delete ${key}:${res}`) return res } }) return observed } //Code test const state = reactive({ foo: 'foo', bar: { a: 1 } }) // 1. Get state.foo // ok // 2. Set existing attribute state.foo = 'fooooooo' // ok // 3. Set non-existent attribute state.dong = 'dong' // ok // 4. Delete attribute delete state.dong // ok Nested Object ResponsivenessTest: Nested objects are not responsive // Set nested object properties react.bar.a = 10 // no ok Add object type recursion // Extract helper method const isObject = val => val !== null && typeof val === 'object' function reactive(obj) { //Judge whether it is an object if (!isObject(obj)) { return obj } const observed = new Proxy(obj, { get (target, key, receiver) { // ... // If it is an object, recursion is needed return isObject(res) ? reactive(res) : res }, //... } Avoid duplicate agentsRepeating agents, such as
Solution : Cache the previous proxy results and use them directly when getting const toProxy = new WeakMap() // same as obj:observed const toRaw = new WeakMap() // same as observed:obj function reactive(obj) { //... // Search cache to avoid duplicate proxy if (toProxy.has(obj)) { return toProxy.get(obj) } if (toRaw.has(obj)) { return obj } const observed = new Proxy(...) // Cache proxy results toProxy.set(obj, observed) toRaw.set(observed, obj) return observed } // Test effect console.log(reactive(data) === state) console.log(reactive(state) === state) SummarizeThis article ends here. I hope it can be helpful to you. I also hope you can pay more attention to more content on 123WORDPRESS.COM! You may also be interested in:
|
<<: About the layout method of content overflow in table
>>: DIV and image horizontal and vertical centering compatible with multiple browsers
This article shares the specific code for impleme...
Table of contents The first step is to download M...
(1) Server configuration: [root@localhost ~]# cd ...
The installation tutorial of mysql 5.7.19 winx64 ...
We don't need to elaborate too much on the ad...
VNC is a remote desktop protocol. Follow the inst...
Install Follow the README to install The document...
Table of contents 01 Introduction to Atomic DDL 0...
Mysql sets boolean type 1. Tinyint type We create...
MySQL is a multi-user managed database that can a...
Yesterday I wanted to use a:visited to change the...
Table of contents PXE implements unattended batch...
Table of contents Tutorial Series 1. Backup strat...
The Docker daemon uses HTTP_PROXY , HTTPS_PROXY ,...
Table of contents 1. Introduction to ReactJS 2. U...