携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第6天,点击查看活动详情
1.v2中哪些情况操作数据不是响应式的?
常见的有以下三种情况
1.给对象后续新增的key进行赋值
data() {
return {
obj:{ }
} }
后续添加 this.obj.age = 18 给age赋值不是响应式的
2.删除对象中的某一项
data(){
return {
obj:{
age:18
}
}
}
delete this.obj.age
3.通过索引去修改数组的元素
data() {
return {
arr: ['a','b','c']
}
}
this.arr[0] = 'd'
2.为什么这些情况不是响应式的?
1.给对象后续新增的key进行赋值
原因:
因为在v2中双向绑定原理是通过Object.defineProperty递归劫持对象中的每一个属性,如果这个属性是后续被添加的,当然就没有劫持到 , 一上来就对对象里面已有的数据进行递归劫持,后续添加的属性没有劫持到
2.删除对象中的某一项
原因
Object.defineProperty不支持对删除操作的劫持
3.通过索引去修改数组的元素
原因
并不是Object.defineProperty不支持对数组的劫持,而是作者出于对性能的原因没有这样做,因为数组里面的内容有很多很多项,对数组的性能不是很好,
3.怎么解决?
1.给对象后续新增的key进行赋值
解决:Vue.set() 或this.$set()
Vue.set(this.obj,'age',18) 也可以换为this.$set
2.删除对象中的某一项
解决:Vue.delete() 或this.$delete()
Vue.delete(this.obj,'age')
3.通过索引去修改数组的元素
解决: Vue.set() 或 this.$set() 或 arr.splice()
Vue.set(this.arr,0,'d')
变更方法 arr.splice(0,1,'d')
4.Vue3呢?
Vue3不存在上述问题
1.给对象后续新增的key进行赋值
Vue3响应式的原理换成了Proxy,可以直接代理整个对象,v2代理的是整个对象的属性, 就无所谓这个属性是不是后续添加的了
2.删除对象中的某一项
Proxy支持对删除操作 2的拦截
3.通过索引去修改数组的元素
Proxy对数组的操作不存在性能问题