Python-Style OO in Javascript

A while a go I wrote a post on Prototype Inheritence in Python. This time, I am somewhat going the opposite direction. That's right: Python-Style OO in Javascript.

Now, I don't think I am the first one who thought of this. In fact, prototype.js does something like this for their method extensions to DOM objects. The main idea is this: if you specify self as the first argument to a method explicitly, you will be able to use self inside of nested closures within the method without having to create a self variable manually, i.e.:

var self = this

or doing something like Function.prototype.bind, or pass the context explicitly around like the Array methods forEach, map, every, etc.


This is but a small proof-of-concept. The result is you can write a class like this:

var Man = Class(Object)({
  __init__: function(self, name){
    self.name = name
  },
  greeting: function(self, other){
    setTimeout(function(){
      self.say("Hello, " + other.name + ", my name is " + self.name)
    }, 100)
  },
  say: function(self, msg){
    sys.puts(msg)
  }
})

Take it for a spin:

var dan = new Man('Dan')
var john = new Man('John')
dan.greeting(john)
john.say('How do?')

Output:

How do?
Hello, John, my name is Dan

The implementation of Class looks like this:

function toArray(args){
  var ret = []
  for (var i = 0; i < args.length; i++)
    ret.push(args[i])
  return ret
}

function Class(parent){
  function bind(func, obj){
    var ret = function(){
      var args = toArray(arguments)
      args.splice(0, 0, obj)
      return func.apply(undefined, args)
    }
    return ret
  }
  
  return function(attrs){
    return function(){
      for (var name in attrs){
        var value = attrs[name]
        if (typeof(value) == 'function'){
          this[name] = bind(value, this)
          this[name].name = name
        }else{
          this[name] = value
        }
      }
      this.__init__.apply(this, arguments)
    }
  }
}

Full source can be found here. I ran it in node. This could be an interesting approach to avoiding "this-hell".


blog comments powered by Disqus