監聽 javascript 對象的變化

       

     廣播: 關注微信公衆號「jQuery每日經典」,有更多資料。微信小程序 -- 前端技術API手冊 也在公衆號首次發佈。有須要的聯繫公衆號中QQ。javascript

  這一章話題的由來,還要從一些學員的做業提及。寫這篇文章主要是想讓你們能從不一樣的角度分析問題,學習的過程當中多看,多練,多想,多查,多用心。在特別多的學習網站中大部分的學習資料基本都是循規蹈矩的,例如慕課網的 javascript 入門教程中,不少講師都講了一些實例,而這些例子中的代碼風格一模一樣,沒什麼新意,並且這些教程佔了很大一部分比例。在這裏,給你們提供另一種思路 ------ 監聽,具體代碼的實現你們本身實現。也歡迎你們評論區寫出不一樣想法。前端

先給出監聽的概念:監聽一個對象的某個屬性是否發生變化,在該屬性變化時當即觸發制定的回調函數。java

實例:購物車,想必你們確定都接觸過,那它的功能如何去實現呢?git

以某寶購物車截圖爲例:github

 

1、功能概述小程序

  1. 選中商品 -- 總數,總價發生變化微信小程序

  2. 增長單類商品數量 -- 總數, 總價,單類商品總價 發生變化微信

  3. 刪除 單類商品 -- 總數總價發生變化函數

2、數據模型學習

    單個商品數據模型{ischeck:是否選中, single:12, count, 2, total:24}

    總商品數據模型{items:商品列表, totalCount:總數, totalPrice:總價}

3、經常使用邏輯

    1. 點擊複選框(選中單類商品),修改總數 和 總價

    代碼格式以下:

var  singleItem = document.getElementById("複選框");
singleItem.點擊事件 = function(){}
    if(this選中){

    總數=總數+this.count;

    總價=總價+this.total;

  } else {

  總數=總數-this.count;

  總價=總價-this.total;

  }
}

4、監聽模式

        監聽模式的另外一個表達方式是觀察者模式,其實並無什麼高級的。購物車這個功能用監聽模式能夠描述爲:當修改什麼的時候,什麼發生變化。

watch(item, 'isCheck', 
  function(newVal, oldVal, obj){
     if(newVal){
       all['totalCount'] = all['totalCount'] + obj['count'];
       all['totalPrice'] = all['totalPrice'] + obj['total'];
     } else {
       ...
     }
});
item['isCheck'] = false;

  

功能實際上是同樣的,只不過是從「當修改什麼的時候,去修改另外的什麼」這種思想轉變爲了「當修改什麼的時候,什麼發生變化」。

 

5、相關資料

1. Object.prototype.watch()

         網址:https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Object/watch

例1:

 

var o {p:1};
o.watch("p",function (id,oldval,newval{
 console.log("o."+id+"由"+oldval+" 變爲 "+newval);
 return newval;  
});
o.p 2;
o.p 3;

上面的代碼顯示結果以下:

o.p 由 1 變爲 2 
o.p 由 2 變爲 3

警告:這個方法是非標準的,僅在Gecko中實現了,而且這方法主要是爲了在調試的時候使用。

 

2. github上也有一些watch.js的項目,

推薦一個:https://github.com/melanke/Watch.JS

具體使用狀況和對它的評價網上有很多,你們能夠看一下。

 

3. 本身實現

  上面代碼中的watch方法實際上是我本身手寫的,粗陋代碼以下:

function watch(obj, prop, callback){  if(prop in obj){    var old = obj[prop];    Object.defineProperty(obj,prop, {      enumerable: true,      configurable: true,      set: function(val) {        var o=old;old=val;        callback(val,o,obj);      },      get:function(){        return old;      }    });  } else {    throw new Error("no such property: " + pro);  }}
相關文章
相關標籤/搜索