Over a million developers have joined DZone.

Prototypes and Private State

· Web Dev Zone

Start coding today to experience the powerful engine that drives data application’s development, brought to you in partnership with Qlik.

 

"private" state in JavaScript means using local state in a constructor function and returning methods which are in scope of that local data. This pattern is not compatible with prototypes.

The following is reposted from Jake Verbaten's blog, Raynos

 

An example:

Live Example

function Parent() {
    // a is private
    var a = 42;

    this.printA() {
        console.log(a);    
    }
}

Parent.prototype.doubleA = function() {
    // How do I access a?
}

There is simply no way you can use "private" state and prototypes because here "private" means local variables inside a constructor.

This is simply the wrong way to do private state. A better solution for private state is a Name. The following examples will use pd to give us an implementation of a Name A Name is a function, given any key will return an object attached to that key.

You can only get that object if you have both the Name and the key. Let's look at an example:

Live Example

var Parent = (function () {
    // "private" Name
    var privates = pd.Name();

    Parent.prototype.doubleA = function() {
        // _ is the unique object
        var _ = privates(this);
        _.a = _.a * 2;
    };

    Parent.prototype.printA = function () {
        // print from the unique object for this instance
        console.log(privates(this).a);    
    };

    return Parent;

    function Parent() {
        // set a on the unique object for this instance
        privates(this).a = 42;
    }
})();

var p = new Parent;
p.doubleA();
p.printA();

Now we can give this a bit of sugar and have an inheritance mechanism using these private Names. Using a function like klass

Live Example:

var Parent = klass(function (privates) {
    // this becomes Parent.prototype
    // Parent becomes the constructor function
    return {
        constructor: function () {
            privates(this).a = 42; 
        },
        printA: function () {
            console.log(privates(this).a);
        }
    };
});

var Child = klass(Parent, function (privates, $super) {
    // the privates Name object is the same as the one used in Parent
    // This becomes Child.prototype. 
    // Child.prototype will inherit from Parent.prototype
    // Child becomes the constructor
    return {
        constructor: function () {
            // $super === Parent.prototype
            $super.constructor.call(this);   
        },
        doubleA: function () {
            var _ = privates(this);
            _.a = _.a * 2;   
        }
    };  
});

var c = new Child;
c.doubleA();
c.printA();

Note that using privates(this).a over this._a has a run-time overhead and a memory overhead.

One needs to choose between "do I want efficient code" or "do I want real hidden state".

 

 

Create data driven applications in Qlik’s free and easy to use coding environment, brought to you in partnership with Qlik.

Topics:

Opinions expressed by DZone contributors are their own.

The best of DZone straight to your inbox.

SEE AN EXAMPLE
Please provide a valid email address.

Thanks for subscribing!

Awesome! Check your inbox to verify your email so you can start receiving the latest in tech news and resources.
Subscribe

{{ parent.title || parent.header.title}}

{{ parent.tldr }}

{{ parent.urlSource.name }}