Wednesday, June 5, 2024
 Popular · Latest · Hot · Upcoming
160
rated 0 times [  163] [ 3]  / answers: 1 / hits: 43456  / 12 Years ago, wed, september 26, 2012, 12:00:00

I understand basic JavaScript pseudo-classes:



function Foo(bar) {
this._bar = bar;
}

Foo.prototype.getBar = function() {
return this._bar;
};

var foo = new Foo('bar');
alert(foo.getBar()); // 'bar'
alert(foo._bar); // 'bar'


I also understand the module pattern, which can emulate encapsulation:



var Foo = (function() {
var _bar;

return {
getBar: function() {
return _bar;
},
setBar: function(bar) {
_bar = bar;
}
};
})();

Foo.setBar('bar');
alert(Foo.getBar()); // 'bar'
alert(Foo._bar); // undefined


But there are un-OOP-like properties to both of these patterns. The former does not provide encapsulation. The latter does not provide instantiation. Both patterns can be modified to support pseudo-inheritance.



What I'd like to know is if there is any pattern that allows:




  • Inheritance

  • Encapsulation (support for private properties/methods)

  • Instantiation (can have multiple instances of the class, each with its own state)


More From » oop

 Answers
12

what about this :



var Foo = (function() {
// private variables
var _bar;

// constructor
function Foo() {};

// add the methods to the prototype so that all of the
// Foo instances can access the private static
Foo.prototype.getBar = function() {
return _bar;
};
Foo.prototype.setBar = function(bar) {
_bar = bar;
};

return Foo;
})();


And now we have instantiation, encapsulation and inheritance.

But, there still is a problem. The private variable is static because it's shared across all instances of Foo. Quick demo :



var a = new Foo();
var b = new Foo();
a.setBar('a');
b.setBar('b');
alert(a.getBar()); // alerts 'b' :(


A better approach might be using conventions for the private variables : any private variable should start with an underscore. This convention is well known and widely used, so when another programmer uses or alters your code and sees a variable starting with underscore, he'll know that it's private, for internal use only and he won't modify it.

Here's the rewrite using this convention :



var Foo = (function() {
// constructor
function Foo() {
this._bar = some value;
};

// add the methods to the prototype so that all of the
// Foo instances can access the private static
Foo.prototype.getBar = function() {
return this._bar;
};
Foo.prototype.setBar = function(bar) {
this._bar = bar;
};

return Foo;
})();


Now we have instantiation, inheritance, but we've lost our encapsulation in favor of conventions :



var a = new Foo();
var b = new Foo();
a.setBar('a');
b.setBar('b');
alert(a.getBar()); // alerts 'a' :)
alert(b.getBar()); // alerts 'b' :)


but the private vars are accessible :



delete a._bar;
b._bar = null;
alert(a.getBar()); // alerts undefined :(
alert(b.getBar()); // alerts null :(

[#82893] Tuesday, September 25, 2012, 12 Years  [reply] [flag answer]
Only authorized users can answer the question. Please sign in first, or register a free account.
alvin

Total Points: 55
Total Questions: 101
Total Answers: 109

Location: Sudan
Member since Tue, Aug 3, 2021
3 Years ago
;