《JavaScript设计模式与开发实践》读书笔记之观察者模式

1.观察者模式

观察者模式定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都将得到通知。

JavaScript中通常采用事件模型替代传统的观察者模式

1.1 逐步实现观察者模式

以客户看房为例

首先指定谁充当发布者,如售楼处

然后给发布者添加一个缓存列表,用于存放回调函数以便通知订阅者。这里为了让订阅者只接收自己感兴趣的消息,增加一个标识key

最后发布消息时候,发布者遍历缓存列表,依次触发里面存放的订阅者的回调函数

var salesOffices={};

salesOffices.clientList=[];

salesOffices.listen=function(key,fn){

    if(!this.clientList[key]){

        this.clientList[key]=[];

    }

    this.clientList[key].push(fn);

}

salesOffices.trigger=function(){

    var key=Array.prototype.shift.call(arguments),

    fns=this.clientList[key];

    if(!fns || fns.length === 0){

        return false;

    }

    for(var i=0,fn;fn=fns[i++];){

        fn.apply(this,arguments);

    }

}



salesOffices.listen('squareMeter88',function(price){//A订阅88平房子消息

    console.log('价格='+price);

});



salesOffices.listen('squareMeter100',function(price)){//B订阅100平房子消息

    console.log('价格='+price);

}



salesOffices.trigger('squareMeter88',200000);

salesOffices.trigger('squareMeter100',300000);

1.2 观察者模式通用实现

var Event=(function(){

    var clientList={},

        listen,

        trigger,

        remove;

    listen=function(key,fn){

        f(!this.clientList[key]){

        this.clientList[key]=[];

        }

        this.clientList[key].push(fn);

    };

    trigger=function(){

        var key=Array.prototype.shift.call(arguments),

        fns=this.clientList[key];

        if(!fns || fns.length === 0){

            return false;

        }

        for(var i=0,fn;fn=fns[i++];){

            fn.apply(this,arguments);

        }

    };

    remove=function(key,fn){

        var fns=clientList[key];

        if(!fns){

            return false;

        }

        if(!fn){

            fns&&(fns.length=0);//没指定fn时,删除全部

        }else{

            for(var l=fns.length-1;l>=0;l--){

                var _fn=fns[l];

                if(_fn === fn){

                    fns.splice(l,1);

                }

            }

        }

    };

    return{

        listen:listen,

        trigger:trigger,

        remove:remove

    }

})();



Event.listen('squareMeter88',function(price){//A订阅88平房子消息

    console.log('价格='+price);

});



Event.trigger('squareMeter88',200000);

 

你可能感兴趣的:(JavaScript)