Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.


Info
titleinfo

My home for all the weirdities of javascript

...

According to MDN (Mozilla Developers Network) info on Closures, "closures are functions that refer to independent (free) variables (variables that are used locally, but defined in an enclosing scope). In other words, these functions 'remember' the environment in which they were created."

So the following piece of code demonstrates this quite nicely

...

The function displayName() declared at line 3 is a closure, notice that it has access to it's enclosing environment.  When you run this code, the alert displays the message "Mozilla".  The function displayName() is able to access the variable name (line 2) because of what javascript terms lexical scoping, which describes how a parser resolves variable names when functions are nested. The word "lexical" refers to the fact that lexical scoping uses the location where a variable is declared within the source code to determine where that variable is available. Nested functions have access to variables declared in their outer scope.

Now consider the following piece of code

...

The reason this works is because all functions in javascript are closures.  closure is the combination of a function and the lexical environment within which that function was declared. This environment consists of any local variables that were in-scope at the time that the closure was created.  According to the MDN the reference to the lexical environment is passed back at line 6.

So what about this interesting piece of code

Code Block
languagejs
titleexample js code
linenumberstrue
function makeAdder(x) {
  return function(y) {
    return x + y;
  };
}

var add5 = makeAdder(5);
var add10 = makeAdder(10);

console.log(add5(2));  // 7
console.log(add10(2)); // 12

The function makeAdder creates a closure that takes a single parameter y.  This parameter should be supplied at the time when the closure is called.  

When lines 7 and 8 are invoked, they both pass the single values 5 and 10.  These values are stored in the closure that is created by makeAdder each time it is invoked, so the value of 5 and 10 are stored in each closure because according to the MDN the lexical environment persists even after the outer closure exits.  So when add5(2) is invoked at line 10, the value of 5 from line 7 has been retained, and similarly for add10(2) at line 11 and line 8 the value 10 has been retained.

This pattern is known in javascript as a function factory.