JavaScript - Closures
JavaScript - Closures
What is Closure?
The concept of closures in JavaScript allows nested functions to access variables defined in the scope of the parent
function, even if the execution of the parent function is finished. In short, you can make global variables local or private
using the closures.
A JavaScript closure is basically a combination of the function and its lexical environment. This allows an inner function
to access the outer function scope. A closure is created every time a function is created at the function creation time.
Before you start learning the concept of closures, you need to know the concept of lexical scoping, nested functions, and
returning functions.
Lexical Scoping
In JavaScript, the lexical scoping is a concept in which the scope of the variables is determined at the code compilation
time based on the structure of the code. For example, the nested function can access the variables from the parent
function's scope is called lexical scoping.
Nested Function
You can define the function inside the function, and the inner function is called the nested function. Let's learn it via the
example below.
Example
In the example below, we have defined the inner() function inside the outer() function. Also, the inner() function is
executed inside the outer() function.
When we execute the outer() function, it also executes the inner() function, a nested function.
<html>
<body>
<p id = "demo"> </p>
<script>
const output = document.getElementById("demo");
function outer() {
output.innerHTML += "The outer function is executed! <br>";
function inner() {
output.innerHTML += "The inner function is executed! <br>"
}
inner();
}
outer();
</script>
</body>
</html>
Output
Returning Function
When any function returns the function instead of a value or variable, it is called the returning function. Let's look at the
example below.
Example
In the below code, the outer() function returns the function definition, and we store it in the 'func' variable. After that, we
use the 'func' variable to invoke a function stored in that.
<html>
<head>
<title> JavaScript - Returning function </title>
</head>
<body>
<p id = "demo"> </p>
<script>
const output = document.getElementById("demo");
function outer() {
output.innerHTML += "The outer function is executed! <br>";
return function inner() {
output.innerHTML += "The inner function is executed! <br>"
}
}
const func = outer();
func();
func();
Output
The above code perfectly works as a decrement counter, but the problem is 'cnt' variable can be accessed in the code
anywhere, and any part of the code can change it without executing the decrement() function.
The decrement() function decreases the value of the 'cnt' by 1 and prints in the output.
The 'func' variable contains the decrement() function expression. Whenever you execute the func(), it calls the
decrement() function.
<html>
<body>
<p id = "demo"> </p>
<script>
const output = document.getElementById("demo");
function counter() {
let cnt = 100; // Works as a global variable for the decrement
return function decrement() {
cnt = cnt - 1;
output.innerHTML += "The value of the cnt is: " + cnt + "<
}
}
const func = counter(); // Returns the decrement() function expre
func();
func();
func();
</script>
</body>
</html>
The full name is John Doe
Benefits of Closure
Followings are some benefits of the closures in JavaScript −
Encapsulation − The closure allows developers to hide or encapsulate the data. It makes data private and
inaccessible from the global scope. So, you can expose only the required variables and functions and hide other
internal details of the code.
Preserving State − The function remembers its lexical scope even if the execution of the outer function is
completed. So, developers can maintain the state as we were maintaining the state of the counter in the above
examples.
Improved memory efficiency − The closure allows you to manage memory efficiently, as you can only retain
access to the necessary variables and don't need to define the variables globally.