双向绑定实现原理vue2、vue3
当一个Vue实例创建时,Vue会遍历data选项的属性,用 Object.defineProperty 将它们转为 getter/setter并且在内部追踪相关依赖,在属性被访问和修改时通知变化。
每个组件实例都有相应的 watcher 程序实例,它会在组件渲染的过程中把属性记录为依赖,之后当依赖项的 setter 被调用时,会通知 watcher重新计算,从而致使它关联的组件得以更新。
vue3使用Proxy代理来实现双向绑定
区别:
- Object.defineProperty一次性只能给对象的一个属性添加get&set方法
- Proxy:一次性给对象所有属性都设置get&set方法
let obj = {}
// 给obj的name属性设置两个方法get&set
Object.defineProperty(obj, 'name', {
set: function (value) {
//value就是给name赋值的结果
console.log('触发了set')
this._name = value //保存这个值 这里不能直接用name,因为会触发set
},
get: function () {
console.log('触发了get')
// 将保存的值返回回来
return this._name
},
})
let obj = {}
let p = new Proxy(obj, {
get: function (obj, prop) {
//obj :被代理的对象 prop:要操作的属性
console.log('触发了get')
return obj[prop]
},
set: function (obj, prop, value) {
// obj:被代理的对象
// prop要赋值的属性
// value要赋值的结果
console.log('触发了set')
// 将赋值的结果保存起来
obj[prop] = value
},
})