Pub/Sub implementations (v28)

Revision 28 of this benchmark created on


Description

Fixed unsubscribe on Higgings-inspired. Loop needs to run backwards to account for the case of duplicate callbacks (once you splice, all subsequent indexes change) - Moved up variable assignment in publish to avoid double array access.

Preparation HTML

<script src="//ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js"></script>
<script>
  /*    
  
        jQuery pub/sub plugin by Peter Higgins (dante@dojotoolkit.org)
  
        Loosely based on Dojo publish/subscribe API, limited in scope. Rewritten blindly.
  
        Original is (c) Dojo Foundation 2004-2010. Released under either AFL or new BSD, see:
        http://dojofoundation.org/license for more information.
  
  */
  (function($) {
   var topics = {};
  
   $.publish1 = function(topic, args) {
    if (topics[topic]) {
     var currentTopic = topics[topic];
  
     for (var i = 0, j = currentTopic.length; i < j; i++) {
      currentTopic[i].apply($, args || []);
     }
    }
   };
  
   $.subscribe1 = function(topic, callback) {
    if (!topics[topic]) {
     topics[topic] = [];
    }
  
    topics[topic].push(callback);
  
    return {
     "topic": topic,
     "callback": callback
    };
   };
  
   $.unsubscribe1 = function(handle) {
    var topic = handle.topic;
  
    if (topics[topic]) {
     var currentTopic = topics[topic];
  
     for (var i = 0, j = currentTopic.length; i < j; i++) {
      if (currentTopic[i] === handle.callback) {
       currentTopic.splice(i, 1);
      }
     }
    }
   };
  
  })(jQuery);
  
(function($) {
 
  var o = $({});
 
  $.subscribe2 = function() {
    o.on.apply(o, arguments);
  };
 
  $.unsubscribe2 = function() {
    o.off.apply(o, arguments);
  };
 
  $.publish2 = function() {
    o.trigger.apply(o, arguments);
  };
 
}(jQuery));  
  
  
  /*
   * Simple Pub/Sub Implementation for jQuery
   *
   * Inspired by work from Peter Higgins (https://github.com/phiggins42/bloody-jquery-plugins/blob/master/pubsub.js)
   *
   * This is about the simplest way to write a pubsub JavaScript implementation for use with jQuery.
   */
  
  (function($) {
   // Cache of all topics
   var topics = {};
  
   // Iterates through all subscribers of a topic and invokes their callback,
   // passing optional arguments.
   $.publish3 = function(topic, args) {
    var thisTopic = topics[topic];

    if (thisTopic) {
     var thisArgs = args || [];
  
     for (var i = 0, j = thisTopic.length; i < j; i++) {
      thisTopic[i].apply($, thisArgs);
     }
    }
   };
  
   // Returns a handle needed for unsubscribing
   $.subscribe3 = function(topic, callback) {
    if (!topics[topic]) {
     topics[topic] = [];
    }
  
    topics[topic].push(callback);
  
    return {
     topic: topic,
     callback: callback
    };
   };
  
   // Removes the subscriber from the particular topic its handle was assigned to
   $.unsubscribe3 = function(handle) {
    var topic = handle.topic;
  
    if (topics[topic]) {
     var thisTopic = topics[topic];
  
     for (var i = thisTopic.length - 1; i >= 0; i--) {
      if (thisTopic[i] === handle.callback) {
       thisTopic.splice(i, 1);
      }
     }
    }
   };
  
  })(jQuery);

(function($) {
  var callbacks, getTopic;
  callbacks = {};
  function getTopic(id) {
    if (!callbacks.hasOwnProperty(id)) {
      callbacks[id] = $.Callbacks();
    }
    return callbacks[id];
  }
  $.publish9 = function(id) {
    getTopic(id).fireWith(null, $.makeArray(arguments).slice(1));  
  }
  $.subscribe9 = function(id, fn) {
    getTopic(id).add(fn);
  }
  $.unsubscribe9 = function(id, fn) {
    getTopic(id).remove(fn);
  }
}(jQuery));


</script>

Test runner

Ready to run.

Testing in
TestOps/sec
Object cache
var handle = $.subscribe1('foo', function() {
 1 + 1;
});

$.publish1('foo', ['bar']);

$.unsubscribe1(handle);
ready
jQuery events
$.subscribe2('foo', function() {
 1 + 1;
});

$.publish2('foo', ['bar']);

$.unsubscribe2('foo');
ready
higgins inspired
var handle = $.subscribe3('foo', function(msg) {
 1 + 1;
});

$.publish3('foo', ['bar']);

$.unsubscribe3(handle);
ready
jQuery callbacks
var handle = $.subscribe9('foo', function(msg) {
 1 + 1;
});

$.publish9('foo', ['bar']);

$.unsubscribe9(handle);
ready

Revisions

You can edit these tests or add more tests to this page by appending /edit to the URL.