Closures In Javascript

What is closure?

A closure is a concept in javascript. A closure is defined as a combination of functions in which we have an outer function and an inner nested function or more functions. The inner function or closure has access to its own global scope, the outer function scope, and the local scope. A closure has access to the outer function's variables and arguments even after the outer function has finished. The inner function has its scope defined by the outer function which is again surrounded by global scope. So inner function can access outer function's scope as well as a global scope. 

function closure(){
 var id = "Closure JS";
 function getId(){ // This is a closure or inner function
   console.log(id); // Has access to outer function variable id here
 }
 getId();
}
closure(); 

In the above example, when we will call closure() function then we will have a variable defined as a local variable in closure function but we don't have any local variable defined in the getId() function. But according to the lexical scope of getId(), function means according to the static scope of the inner function when it is defined, it can access the variable id from its outer function's scope.

What is the lexical scope? 

It is the static scope for accessing the variables, functions, objects or arguments in Javascript on the basis where it is defined while writing the code. The lexical scope helps the parser to resolve the function names in case of outer and inner functions(called as nested functions). 

Example Of Closure

Now we will see an example of closure as shown below:

function counter(){
  var count = 0;
  function inner(){ // closure here
    alert(++count);
 }
  return inner;
}
var myCounter = counter();
myCounter();

In this case, the count variable exists even after the function counter has finished because the inner function has form closures here. So at the time of defining the inner function, it has access to the outer function's variable count. So variable count exists in the lexical environment of the inner function. When we create myCounter reference, it is an instance of the inner function. So it can access the variable counter easily.

Reuse Of Code Using Closure

We can reuse closure in the following way to avoid writing the heavy tasks again and again.

function fetchData(url) {
     return function inner() {  // this is closure here which can access the url argument of outer function
      const response = this.http.get(url);  // do heavy task of getting or fetching data here
      return response.data;
  };
}
 function fetchDataForCustomerA(pathA) {  
    const urlPath = fetchData('some URL');
    const result = urlPath(); 
};

 function fetchDataForCustomerB(pathB) {
    const urlPath = fetchData('some URL');
    const result =  urlPath(); 
};

We can use closure for the reusability of code. In the above example, fetchData is a function that takes an argument URL and returns an inner function which will do the heavy task of fetching data, posting data, etc. In this example, I have used angular HTTP requests to make a get call. You can do any heavy task inside this inner function. We can pass different URLs for different customer's request and we just have to call the fetchData() function passing the appropriate URL for that customer. Then we have to call the inner function using the urlPath() to fetch the results.

Comments