When we have code like:
function a(){
var x =0;
this.add=function(){
alert(x++);
}
}
var test = new a();
test.add(); // alert 0
test.add(); // alert 1
test.add(); // alert 2
How does this work?
Doesn’t that the value of ‘x’ in a() should be ‘gone’ as soon as test = new a() is complete? The stack contains x should also be gone as well, right? Or, does javascript always keep all the stacks ever created in case they will be referenced in future? But that wouldn’t be nice, would it…?
What you’re seeing is the effect of a closure. The function being defined within the other function gets access to all of the variables and such in scope where it is — even after the outer function returns. More here, but basically, the variables (and arguments) in the function all exist as properties on an object (called the “variable object”) related to that function call. Because the function you’ve bound to
this.addis defined within that context, it has an enduring reference to that object, preventing the object from being garbage-collected, which means that that function can continue to access those properties (e.g., the variables and arguments to the function).You normally hear people saying that the function closes over the
xvariable, but it’s more complex (and interesting) than that. It’s the access to the variable object that endures. This has implications. For instance:At first glance, we see that the click handler only ever uses
x. So it only has a reference tox, right?Wrong, the reference is to the variable object, which contains
xandbigarray. Sobigarray‘s contents will stick around as well, even though the function doesn’t use them. This isn’t a problem (and it’s frequently useful), but it emphasizes the underlying mechanism. (And if you really don’t needbigarray‘s contents within the click handler, you might want to dobigarray = undefined;before returning fromfoojust so the contents are released.)