1.基本理解Object.defineProperty
Object.defineProperty()可以给对象添加新的属性,也可以修改本身的属性
1.1简单的理解
是利用defineproperty来实现具体来说是对data里的属性都设置了getter和setter,getter收集依赖就是收集每个标签和每个数据属性的对应关系,当data对象中属性修改赋值的时候就会触发对应的setter函数拦截进行视图更新
1751872982884.png
2.深入理解Object.defineProperty
当Object.defineProperty()这个方法改变自身属性时,比如给自身name属性添加get(),和set()方法时,就会出现错误,虽然表面上方法添加上了,但实质上是一种错误的表现形式
let data={
name:"一元教育"
}
//死循环,当你读取data.name时,调用get(),然后一直读取,进入死循环,当你改变data.name值,一直在改变,进入新的死循环
Object.defineProperty(data,'name',{
get(){
return data.name
},
set(val){
data.name=val
}
})
3.更深层理解该方法
我们学Vue的时候,它里面原生写数据代理就涉及到该方法,具体内容,我一 一说开,构造一个名为vm的Vue对象 ,数据代理表面上是指vm._data=data;将data里面的数据对象赋值给新的对象_data,但_datal里面的内容不止如此,里面有get(),set(),这个时候要写一段代码说明用该方法如何使用使得Vue对象里面检测是否添加get()set()方法,递归思想,只要data数据里面存在对象,就能给对象对应的属性添加这两种方法,下面的代码只考虑一层
<script>
let data={
realname:"bob",
id:"001",
age:28
}
//创建一个监视的实例对象,用与监视data中属性的变化
const obs=new Observer(data);
function Observer(obj){
const keys=Object.keys(obj);
keys.forEach((k)=>{
//给传过来的实例对象data里面的属性添加getter,setter方法
Object.defineProperty(this,k,{
get(){
return obj[k]
},
set(val){
console.log(`${k}被改了,我要解析模板,生成虚拟DOM,忙碌`);
obj[k]=val
}
})
})
}
console.log(obs);
data=obs;
console.log(data);
let vm={};
vm._data= data;
</script>