Today while reviewing some code a junior wrote - I saw a 'class' definition that looked like this -
--------------------------------------------
function Foo(x, y) {
var innerx = x*10;
var innery = y*50;
... some more processing here ...
var returned = {};
returned.sum = function () {
return innerx+innery;
};
returned.setx = function (xval) {
innerx = xval;
};
return returned;
}
var newFoo = Foo();
--------------------------------------------
Do you see what is happening here? This code is using closures to mimic object encapsulation in javascript. The returned object is a closure and therefore has access to innerx and innery variables of the enclosing object/function. The piece of code that calls Foo() gets this object but cannot access the inner variables. It can only access the setx() method to set the value of innerx. And innery is completely inaccessible. This is functional paradigm not an object oriented one (notice the distinct absence of new anywhere in the code)!
There isn't a way to do this using plain prototype mechanism provided by javascript. You would write something like -
--------------------------------------------
function Foo(x, y) {
this.innerx = x*10;
this.innery = y*50;
... some more processing here ...
}
Foo.prototype.sum = function(){
return innerx+innery;
};
Foo.prototype.setx = function(xval){
this.innerx = xval;
};
var newFoo = new Foo();
--------------------------------------------
Here the variables innerx and innery are exposed to the world. But that's not such a bad thing in my opinion - power == responsibility.
But the functional style code (using closures) has another problem - For each object that is created, the methods are redefined! This is a great speed and memory overhead if your methods are small. In the prototypal code, the methods are defined once (for the prototype object) and then shared across all instances.
The verdict - I told the coder to rewrite the code using the prototype object. There really wasn't a need to support strict encapsulation in this piece of code (in my experience, there rarely is) and the performance hit wasn't worth it.
No comments:
Post a Comment