Book Image

Learning jQuery : Better Interaction Design and Web Development with Simple JavaScript Techniques

Book Image

Learning jQuery : Better Interaction Design and Web Development with Simple JavaScript Techniques

Overview of this book

Table of Contents (18 chapters)
Learning jQuery
Credits
About the Authors
About the Reviewers
Preface

Variable Scoping


Inner functions can of course have their own variables, which are restricted in scope to the function itself:

function outerFun() {
  function innerFun() {
    var innerVar = 0;
    innerVar++;
    alert(innerVar);
  }
  return innerFun;
}

Each time the function is called, through a reference or otherwise, a new variable innerVar is created, incremented, and displayed:

var globVar = outerFun();
globVar(); // Alerts "1"
globVar(); // Alerts "1"
var innerVar2 = outerFun();
innerVar2(); // Alerts "1"
innerVar2(); // Alerts "1"

Inner functions can reference global variables, in the same way as any other function can:

var globVar = 0;
function outerFun() {
  function innerFun() {
    globVar++;
    alert(globVar);
  }
  return innerFun;
}

Now our function will consistently increment the variable with each call:

var globVar = outerFun();
globVar(); // Alerts "1"
globVar(); // Alerts "2"
var globVar2 = outerFun();
globVar2(); // Alerts "3"
globVar2(); // Alerts "4"

But what if the variable is local to the parent function? Since the inner function inherits its parent’s scope, this variable can be referenced too:

function outerFun() {
  var outerVar = 0;
  function innerFun() {
    outerVar++;
    alert(outerVar);
  }
  return innerFun;
}

Now our function calls have more interesting behavior:

var globVar = outerFun();
globVar(); // Alerts "1"
globVar(); // Alerts "2"
var globVar2 = outerFun();
globVar2(); // Alerts "1"
globVar2(); // Alerts "2"

We get a mix of the two earlier effects. The calls to innerFun() through each reference increment innerVar independently. Note that the second call to outerFun() is not resetting the value of innerVar, but rather creating a new instance of innerVar, bound to the scope of the second function call. The upshot of this is that after the above calls, another call to globVar() will alert 3, and a subsequent call to globVar2() will also alert 3. The two counters are completely separate.

When a reference to an inner function finds its way outside of the scope in which the function was defined, this creates a closure on that function. We call variables that are not local to the inner function free variables, and the environment of the outer function call closes them. Essentially, the fact that the function refers to a local variable in the outer function grants the variable a stay of execution. The memory is not released when the function completes, as it is still needed by the closure.