JS发布订阅模式

JS发布订阅模式

一、直白的发布订阅例子

简单的售楼处例子:

  1. 售楼处是发布者

    var salesOffices = {
         };
    
  2. 添加订阅者的方法,以一个函数代表一个订阅者

    /**
     * 增加订阅者
     * 
     * @param {Function} fn 发送消息给订阅者的函数
     */
    salesOffices.listen = function (fn) {
         
        this.clientList.push(fn)
    }
    
  3. 发布消息的方法

    salesOffices.trigger = function () {
         
        for (var i = 0; i < this.clientList.length; i++) {
         
        	fn = this.clientList[i]
            fn.apply(this, arguments)
        }
    }
    
  4. 测试

    // 添加订阅者小明
    salesOffices.listen(function (price, squareMeter) {
         
        console.log('price', price)
        console.log('squareMeter', squareMeter)
    })
    
    // 添加订阅者小红
    salesOffices.listen(function (price, squareMeter){
         
        console.log('price', price)
        console.log('squareMeter', squareMeter)
    })
    
    salesOffices.trigger(2000000, 100)
    // price 2000000
    // squareMeter 100
    // price 2000000
    // squareMeter 100
    

二、用户只订阅自己感兴趣的消息

  1. 售楼处是发布者

    var salesOffices = {
         };
    
  2. 添加订阅者的方法,以一个函数代表一个订阅者

    /**
     * 增加通知订阅者
     * @param {Function} fn  发送消息给订阅者的函数
     * @param {String} event 代表某一类消息
     */
    salesOffices.listen = function (event, fn) {
         
    
    	// 如果还没有此类消息,给该类消息创建一个缓存列表
    	if (!this.clientList[event]) {
         
    		this.clientList[event] = []
    	} 
        this.clientList.push(fn)
    }
    
  3. 发布消息的方法

    /**
     * 发布消息给所有订阅此消息的人
     * 
     * @param {String} event 代表某一类消息
     * @param {*} message 发送的消息
     */
    salesOffices.trigger = function (event, message) {
         
    
    	// 消息标签下的订阅者
    	var subscriberFuncs = this.clientList[event]
    	
    	// 如果没有此标签或消息标签下没有订阅者
    	if (!subscriberFuncs || subscriberFuncs.length === 0) {
         
        	console.log('No subscribers')
        	return false
    	}
    
    	// 发布消息
        for (var i = 0, fn; fn = fns[i++]; ) {
         
            subscriberFuncs.apply(this, message)
        }
    }
    
  4. 测试

    // 测试:
    // 添加订阅者小明
    // 小明订阅了88平米房的信息
    salesOffices.listen('squareMeter88', function(price) {
         
    	console.log('price', price)
    })
    
    // 添加订阅者小红
    // 小明订阅了95平米房的信息
    salesOffices.listen('squareMeter95', function(price) {
         
    	console.log('price', price)
    })
    
    // 添加订阅者小李
    // 小明订阅了95平米房的信息
    salesOffices.listen('squareMeter95', function(price) {
         
    	console.log('price', price)
    })
    
    // 发布 88 平方米房子的价格
    salesOffices.trigger('squareMeter88', 2000000);
    // price 2000000 (通知小明)
    
    // 发布 95 平方米房子的价格
    salesOffices.trigger('squareMeter95', 2000000);
    // price 2000000 (通知小红)
    // price 2000000 (通知小李)
    
    // 发布 1000 平方米房子的价格
    salesOffices.trigger('squareMeter1000', 2000000);
    // No subscribers
    

三、发布订阅模式的通用实现

考虑到代码复用性,将发布—订阅的功能提取出来,放在一个单独的对象内 (Event)

  1. 定义发布者通用的基本属性和方法

    var Event = {
         
    	/**
    	 * 储存不同类消息下以及其下的订阅者
    	 */
        clientList: 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值