JavaScript: Self-invoking anonymous function blocks
We have learnt scopes and closures in JavaScript with my previous posts. Combining these two core concepts, JavaScript gives us a beautiful syntax called self-invoking anonymous functions. It simply means an unnamed function that executes itself. This special syntax can give us some extraordinary powers 💪,
- Power to expose only selected set of variables and methods to its outer scope.
- Power to close down on variable and method name clashes with other code blocks or third party libraries.
- Power to control JavaScript asynchronous executions.
- With all the above powers, comes the greater responsibility of writing your open source libraries for JavaScript using self-invoking anonymous function blocks.
Now let's take a look at its syntax. It's very simple.
The syntax is self-explanatory. Why self-invoking? Because the last ()
brackets executes the function. Why anonymous? Because the function doesn't have a name. You can have as many anonymous functions as you want in JavaScript.
One rule to declare anonymous functions is to have a wrapping()
brackets. In other words, you can pass an anonymous function where ever you see a wrapping()
brackets. Eg,
Now let's take a look at how self-invoking anonymous functions or self-executing anonymous functions give you all the powers that we talked about earlier.
Power to expose a selected set of variables and methods to the outer scope.
Let's take a code example,
You can see that the private methods and variables are well encapsulated within our anonymous function, make themselves available within the block, but not outside.
Power to close down on variable and method name clashes with other code blocks or third party libraries.
Again let's look this through code example,
Both of those self-executing anonymous functions have same-named variables and methods. But they never complain that the variable is already declared. Thus it avoids clashes with other libraries and code blocks.
Power to control JavaScript asynchronous executions.
Let's take this code,
I have been asked this exact question in many interviews. Anyone assessing the code would think the console.log
will print,
prints: 0 // after 0 second
prints: 1 // after 1 second
prints: 2 // after 2 seconds
prints: 3 // after 3 seconds
prints: 4 // after 4 seconds
And if you have answered the above, the interviewer might have kicked you out of the door! And if he doesn't, you please kick him out.
The answer for the above code is quite different and it is,
prints: 5 // after 0 seconds
prints: 5 // after 1 seconds
prints: 5 // after 2 seconds
prints: 5 // after 3 seconds
prints: 5 // after 4 seconds
Yes, it prints '5' five times at various intervals!
This is because the JavaScript event loop executes the code in a unique order. It priorities synchronous operations (in this code example it is the for
loop) over asynchronous operations. So, the for
loop registers all setTimeout
for later execution. By the time for
finishes, the value for variable i
is 5
in the memory. Then comes the asynchronous operations like setTimeout
. And this is why the console.log
can only read 5
for variable i
from the memory.
How can we fix this? The magic power here is the self-invoking anonymous functions. How is it going to help? let's take a look,
The above code will print exactly the result we wanted,
prints: 0 // after 0 second
prints: 1 // after 1 second
prints: 2 // after 2 seconds
prints: 3 // after 3 seconds
prints: 4 // after 4 seconds
Self-invoking anonymous functions give an individual private scope of i
for each setTimeout
we register to JavaScript event loop or eval loop. It means we have five times i
declared with different values from 0 to 4 in the memory, each with its scope wrapped. Pure magic 🧝♀️!
In real-world project building, you might be asked to write a code to fetch a list of songs from an API and for each song, you will be asked to fetch its artist name using a different API. Something like this,
If you are following my post keenly, you would have immediately caught what's wrong with the above code. How to fix it? With the magic self-invoking anonymous function voila!
Last but not least,
Power of writing your libraries
Great soles who wrote popular libraries like JQuery, underscore or lodash would have started writing their first line of code with self-invoking anonymous function for their libraries. Request you to go and read the open-source library's codebase. You can learn a lot more from them.
Now that you know everything about it, you have the power to start writing your JavaScript library.
If you have reached this far, precious 💍 things in life will find your way.
With that note, adios.