// const ins = new Vue({
// data: {
// a: 1
// }
// })
// ins.$watch('a', () => {
// console.log('修改了a')
// })
// 问题1:避免收集重复依赖
// 问题2:如何深度观测
// 问题3:如何处理数组及其他边界条件
// const data = {
// a: 1,
// b: 2
// }
// function walk (data) {
// for (const key in data) {
// const dep = []
// let val = data[key]
// Object.defineProperty(data, 'a', {
// get: function () {
// console.log('获取a的值')
// // 获取属性值时,收集依赖
// dep.push(Target)
// return val
// },
// set: function (newVal) {
// console.log('设置a的值')
// if (newVal === val) return
// // 设置属性值时,执行依赖
// dep.forEach(fn => fn())
// }
// })
// }
// }
// let Target = null
// function $watch (exp, fn) {
// Target = fn
// data[exp]
// }
// $watch('a', () => { console.log(111) })
// data.a = 2
// console.log('test', data.a)
// 如果嵌套对象,只能检测到第一层对象属性
const data = {
a: {
b: 1
}
}
let Target = null
function walk (data) {
for (let key in data) {
const dep = []
let val = data[key]
if (typeof data[key] === 'object') {
walk(val)
}
Object.defineProperty(data, key, {
get() {
dep.push(Target)
console.log('val', val)
console.log('dep', dep)
return val
},
set(newVal) {
if (newVal === val) return
val = newVal
dep.forEach(fn => fn())
}
})
}
}
walk(data)
//exp参考:'a'\'a.b'
function $watch (exp, fn) {
Target = fn
let obj = data
if(/\./.test(exp)) {
let keys = exp.split('.')
for (let key of keys) {
obj = obj[key]
}
return
}
data[exp]
}
// 当watch的是个fn
function $watch (src, fn) {
}