DEV Community

Daniel Zaltsman
Daniel Zaltsman

Posted on

Javascript Closures

What is a Closure?

Closures are an important concept in javascript, defined as the combination of a function bundled together (enclosed) with references to its surrounding state (the lexical environment). In other words, a closure gives you access to an outer function’s scope from an inner function. In JavaScript, closures are created every time a function is created, at function creation time in MDN.

Let's test out a function's ability to grab outer function variables with a custom function maker.

Image from Gyazo

For this customFunctionMaker, we pass in an operator as a string and a number to increment or decrement by. Our goal is to return a function that decrements any number by 7. That's where closures come in.

Because I am able to access an outer function's scope, I can always use the parameters passed into the outer functions(which are essentially local variables initialized in the outer function scope). Let's use them to alter the function that is returned in the inner function.

Image from Gyazo

I have some questions before we get into the example, try to answer them:

1: What does customFunctionMaker return?

2: What does the environment look like for decrementBySeven(variables, parameters,etc.)?

3: What changes when we use different arguments for customFunctionMaker?


Answer:

1: customFunctionMaker returns that function defined inside of it and does not change. Therefore, decrementBySeven equals that anonymous inner function.

2: Currently, decrementBySeven has access to the arguments passed through the customFunctionMaker function for that instance.

3: The initialized local variables in the scope will change in that instance, and therefore the anonymous function will have access to different arguments.

Let's test out the the new function we created.

Image from Gyazo

Awesome! We created a function with a function. That's pretty neat. So why does this work?

Because the inner function has access to our arguments put into this particular instance of the first function. Let's make another shall we?

Image from Gyazo

Now we've piped the output from the decrementBySeven function into the increaseByFour function. The numbers add up so let's give ourselves a pat on the back for getting a little funky. In the increaseByFour function, it has its own environment containing the addition operator as a string and the number 4. But we are only calling the inner anonymous function along with the parameter passed through it.

Closures can also be useful for creating private methods. This is useful considering there is no way to do it natively in Javascript, compared to other languages.

Let's ask ourselves those same few questions as the last example:

1: What does makeCounter return?

2: What does the environment look like for counter1(variables, parameters,etc.)?


Answer:

1: makeCounter will return an object containing functions.

2: Those functions in the returned object will have access to their own particular instance of privateCounter, and the function changeBy. This means that counter1 can call those object methods and increment, decrement, or show value of their own particular privateCounter.

Image from Gyazo

Notice how counter2's value never changed, even though counter1's did. They have access to their own private methods and counters. This is all thanks to closures. They have access to their own scope and privateCounter instances.

Top comments (0)