<!DOCTYPE html> <html lang="en"> <head> <title></title> </head> <body> <div> <p class="box"></p> <ul class="hobby"></ul> </div> <script> var box = document.querySelector('.box'); var hobby = document.querySelector('.hobby') class Observer{ constructor(data){ this.data = data this.filterObj(data) } // 判斷傳入的參數的數據類型是否是一個對象 static isObject(obj){ if(Object.prototype.toString.call(obj) === '[object Object]'){ return true }else{ return false } } filterObj(data){ // 若是不是對象則結束 if(!Observer.isObject(data)){ return } for(const key in data){ // 過濾對象上面的屬性 if(data.hasOwnProperty(key)){ const value = data[key] // 若是data的屬性值爲對象 if(Observer.isObject(data[key])){ new Observer(data[key]) } this.watch(key,value) } } } watch(k,v){ Object.defineProperty(this.data,k,{ enumerable:true, configurable:true, get:function(){ console.log(`${k}`, ' -- 被訪問') return v }, set:function(newval){ console.log(`${k}`,'-- 發生變化') console.log('新值爲 : ',JSON.stringify(newval)) // 當值發生改變時候修改頁面元素中的內容 box.innerHTML = newval // 先清空元素中的內容 hobby.innerHTML='' createLi(newval) // 是不是一個對象 if(Observer.isObject(newval)){ new Observer(newval) } v = newval } }) } } let obj = { num:2048, hobby:['唱歌','睡覺','打豆豆'], equipment:{ arms:'kuku', armgurd:'lobg' } } box.innerHTML = obj.num; hobby.innerHTML = '' function createLi (arr){ for(let i in arr){ hobby.innerHTML += `<li>${arr[i]}</li>` } } createLi(obj.hobby) let ss = new Observer(obj) console.log(ss); </script> </body> </html>