JavaScript中发布/订阅模式的简单实例


Posted in Javascript onNovember 05, 2014

上次研究观察者模式,很多文章说它也叫Subscribe/Publish(发布/订阅模式)。可在《Javascript设计模式》一书中,这两种模式还是有些区别的。书中原话如下:

1.Observer模式要求希望接收到主题通知者的观察者必须订阅内容改变的事件。

2.Subscribe/Publish模式使用了一个主题/事件通道,这个通道介于订阅者和发布者之间。该事件系统允许代码定义应用程序的特定事件,该事件可以传递自定义参数,自定义参数包含订阅者所需要的值。其目的是避免订阅者和发布者产生依赖关系。

与Observer模式不同之处在于它允许任何订阅者执行适当的事件处理程序来注册和接收发布者发出的通知。

好吧,不明觉厉。下面是我的理解:

1.观察者模式中,目标对象负责维护观察者。发布/订阅模式中发布者不关心订阅者,只负责把消息丢出去就不管了。

2.观察者模式中,观察者要提供一个接口,然后当目标对象发生改变时调用此接口使自身状态和目标状态保持一致。即所有的观察者都要有一个统一的接口(比如上文中写的update方法,大家的方法都要叫这个名字)。而发布/订阅模式中,订阅者事件的触发不是依靠这样一个接口,而是订阅者通过监听一个特定的消息(这个消息一般包含名称和订阅者所需要的参数)来触发的。可以理解为订阅者监听的不是发布者,而是消息池,只要消息池里有它关心的消息,即触发事件,不管这个消息是谁发布过去的。发布者和订阅者是解耦的。

下面是js中发布/订阅模式的实现,复制粘贴到console里面试一试就明白了:

var pubsub = (function(){

    var q = {}

        topics = {},

        subUid = -1;

    //发布消息

    q.publish = function(topic, args) {

        if(!topics[topic]) {return;}

        var subs = topics[topic],

            len = subs.length;

        while(len--) {

            subs[len].func(topic, args);

        }

        return this;

    };

    //订阅事件

    q.subscribe = function(topic, func) {

        topics[topic] = topics[topic] ? topics[topic] : [];

        var token = (++subUid).toString();

        topics[topic].push({

            token : token,

            func : func

        });

        return token;

    };

    return q;

    //取消订阅就不写了,遍历topics,然后通过保存前面返回token,删除指定元素

})();

//触发的事件

var logmsg = function(topics, data) {

    console.log("logging:" + topics + ":" + data);

}

//监听指定的消息'msgName'

var sub = pubsub.subscribe('msgName', logmsg);

//发布消息'msgName'

pubsub.publish('msgName', 'hello world');

//发布无人监听的消息'msgName1'

pubsub.publish('anotherMsgName', 'me too!');
Javascript 相关文章推荐
window.open不被拦截的实现代码
Aug 22 Javascript
js函数获取html中className所在的内容并去除标签
Sep 08 Javascript
jquery中获取id值方法小结
Sep 22 Javascript
JQuery性能优化的几点建议
May 14 Javascript
jQuery实现的图片轮播效果完整示例
Sep 12 Javascript
javascript表单控件实例讲解
Sep 13 Javascript
javascript 使用正则test( )第一次是 true,第二次是false
Feb 22 Javascript
node安装--linux下的快速安装教程
Mar 21 Javascript
JS 正则表达式验证密码、邮箱格式的实例代码
Oct 28 Javascript
vue.js仿hover效果的实现方法示例
Jan 28 Javascript
js canvas实现俄罗斯方块
Oct 11 Javascript
JS的深浅复制详细
Oct 16 Javascript
JavaScript不刷新实现浏览器的前进后退功能
Nov 05 #Javascript
Javascript检查图片大小不要让大图片撑破页面
Nov 04 #Javascript
node.js开发中使用Node Supervisor实现监测文件修改并自动重启应用
Nov 04 #Javascript
node.js中Socket.IO的进阶使用技巧
Nov 04 #Javascript
node.js中的Socket.IO使用实例
Nov 04 #Javascript
Node.js的特点和应用场景介绍
Nov 04 #Javascript
Node.js中的模块机制学习笔记
Nov 04 #Javascript
You might like
跟我学Laravel之请求与输入
2014/10/15 PHP
Laravel5中Cookie的使用详解
2017/05/03 PHP
php curl批处理实现可控并发异步操作示例
2018/05/09 PHP
如何在PHP中使用AES加密算法加密数据
2020/06/24 PHP
2种jQuery 实现刮刮卡效果
2015/02/01 Javascript
JS实现CheckBox复选框全选全不选功能
2015/05/06 Javascript
使用requestAnimationFrame实现js动画性能好
2015/08/06 Javascript
jQuery实现的Div窗口震动效果实例
2015/08/07 Javascript
JS实现的车标图片提示效果代码
2015/10/10 Javascript
在Ubuntu系统上安装Node.JS的教程
2015/10/15 Javascript
AngularJS基础 ng-mouseover 指令简单示例
2016/08/02 Javascript
JS 拼凑字符串的简单实例
2016/09/02 Javascript
微信小程序 rpx 尺寸单位详细介绍
2016/10/13 Javascript
JavaScript将base64图片转换成formData并通过AJAX提交的实现方法
2016/10/24 Javascript
javascript 删除数组元素和清空数组的简单方法
2017/02/24 Javascript
vue-resouce设置请求头的三种方法
2017/09/12 Javascript
javascript+html5+css3自定义弹出窗口效果
2017/10/26 Javascript
使用VUE实现在table中文字信息超过5个隐藏鼠标移到时弹窗显示全部
2019/09/16 Javascript
Jquery 获取相同NAME 或者id删除行操作
2020/08/24 jQuery
[04:31]2016国际邀请赛中国区预选赛妖精采访
2016/06/27 DOTA
python发布模块的步骤分享
2014/02/21 Python
关于反爬虫的一些简单总结
2017/12/13 Python
python如何求解两数的最大公约数
2018/09/27 Python
使用python3实现操作串口详解
2019/01/01 Python
在pytorch中查看可训练参数的例子
2019/08/18 Python
Python 闭包,函数分隔作用域,nonlocal声明非局部变量操作示例
2019/10/14 Python
英国时尚饰品和发饰购物网站:Claire’s
2017/07/04 全球购物
财务会计专业毕业生自荐信
2013/10/02 职场文书
岗位职责的构建方法
2014/02/01 职场文书
小学毕业感言150字
2014/02/05 职场文书
村党支部对照检查材料思想汇报
2014/09/28 职场文书
2014年食品安全工作总结
2014/12/04 职场文书
2015年幼儿园元旦亲子活动方案
2014/12/09 职场文书
Python requests库参数提交的注意事项总结
2021/03/29 Python
Python如何使用logging为Flask增加logid
2021/03/30 Python
python源码剖析之PyObject详解
2021/05/18 Python