javascript之观察者模式
demo1:
var global = window; (function(ns, base){ //被观察的对象 function Observable(){ this.observers = {}; } Observable.prototype = { //subscribe bind: function(name, observer){ var observers = this.observers[name] || ( this.observers[name] = [] ); var isbind = observer && observers.indexOf(observer) === -1; if(isbind){ observers.push(observer); } }, //unsubscribe unbind: function(name, observer){ var observers = this.observers[name], index = observers && observers.indexOf(observer), isunbind = (index !== undefined) && (index > -1); if (isunbind ){ observers.splice(index, 1); } }, //publish trigger: function (name, args){ var observers = this.observers[name]; if(!observers) return; for (var i=0; i<observers.length; i++) { observers[i](args); } } }; Observable.fn = Observable.prototype; ns.Observable = Observable; }(global, undefined)); //测试,Model和View解耦 (function(){ //UserModel,继承Observable function UserModel (id){ this.id = id; } UserModel.prototype = new Observable(); UserModel.prototype.load = function(){ //ajax load var mode = { name: "jser", id: this.id }; //触发loaded事件 this.trigger("loaded", { target: this, data: mode } ); } function UserView(){ this.render = function(data){ alert("username: "+ data.name); } } var user = new UserModel(); var view = new UserView(); //添加观察者,当UserMode加载完成调用 user.bind("loaded", function(event){ view.render(event.data); }); user.load(); }());
demo2:
function Observer() { this.fns = []; } Observer.prototype = { subscribe: function (fn) { this.fns.push(fn); }, unsubscribe: function (fn) { this.fns = this.fns.filter( function (el) { if (el !== fn) { return el; } } ); }, update: function (o, thisObj) { var scope = thisObj || window; this.fns.forEach( function (el) { el.call(scope, o); } ); } }; //测试 var o = new Observer; var f1 = function (data) { console.log('Robbin: ' + data + ', 赶紧干活了!'); }; var f2 = function (data) { console.log('Randall: ' + data + ', 找他加点工资去!'); }; o.subscribe(f1); o.subscribe(f2); o.update("Tom回来了!") //退订f1 o.unsubscribe(f1); //再来验证 o.update("Tom回来了!");
if (!Array.prototype.forEach) { Array.prototype.forEach = function (fn, thisObj) { var scope = thisObj || window; for (var i = 0, j = this.length; i < j; ++i) { fn.call(scope, this[i], i, this); } }; } if (!Array.prototype.filter) { Array.prototype.filter = function (fn, thisObj) { var scope = thisObj || window; var a = []; for (var i = 0, j = this.length; i < j; ++i) { if (!fn.call(scope, this[i], i, this)) { continue; } a.push(this[i]); } return a; }; }
demo3:
//通用代码 var observer = { //订阅 addSubscriber: function (callback) { this.subscribers[this.subscribers.length] = callback; }, //退订 removeSubscriber: function (callback) { for (var i = 0; i < this.subscribers.length; i++) { if (this.subscribers[i] === callback) { delete (this.subscribers[i]); } } }, //发布 publish: function (what) { for (var i = 0; i < this.subscribers.length; i++) { if (typeof this.subscribers[i] === 'function') { this.subscribers[i](what); } } }, // 将对象o具有观察者功能 make: function (o) { for (var i in this) { o[i] = this[i]; o.subscribers = []; } } }; var blogger = { recommend: function (id) { var msg = 'dudu 推荐了的帖子:' + id; this.publish(msg); } }; var user = { vote: function (id) { var msg = '有人投票了!ID=' + id; this.publish(msg); } }; observer.make(blogger); observer.make(user); var tom = { read: function (what) { console.log('Tom看到了如下信息:' + what) } }; var mm = { show: function (what) { console.log('mm看到了如下信息:' + what) } }; // 订阅 blogger.addSubscriber(tom.read); blogger.addSubscriber(mm.show); blogger.recommend(123); //调用发布 //退订 blogger.removeSubscriber(mm.show); blogger.recommend(456); //调用发布 //另外一个对象的订阅 user.addSubscriber(mm.show); user.vote(789); //调用发布
参考地址:1 http://www.cnblogs.com/rentj1/archive/2013/01/08/2851383.html
2 http://www.cnblogs.com/TomXu/archive/2012/03/02/2355128.html
posted on 2013-04-28 15:33 Ijavascript 阅读(188) 评论(0) 编辑 收藏 举报