Fun with Hoisting
In today’s TL;DR series, we’ll talk about hoisting. Click here to know more about the TL;DR series.
In JavaScript, all variable declarations using var are hoisted to the top of its function scope or the global scope. Here are the key rules:
- Function declarations are hoisted above variable declarations.
- Function expressions are not hoisted.
- Variable assignments are not hoisted.
- Avariables assigned a value before being declared are automatically part of the global scope.
- Declarations are hosted to the top of function blocks, not code blocks
Function declarations are hoisted above variable declarations.
After hoisting takes place, it looks like the following:
function foo(){};
var foo;
console.log(typeof foo)
Hoisting Moves Declarations to the Top of Code Blocks
The output is undefined! This is because var x; within the if block is hoisted to the top of the function. The x=1 assignment is kept in the if block so x is never assigned a value. After hoisting, the code looks like the following:
function foo(){
var x;
if (false){
x = 1;
}
console.log(x);
Remember, variable assignment does not get hoisted
After hoisting, the code is interpreted like:
var foo;
function foo(){};
foo = "abc";
Variable assignments are NOT Hoisted
After hoisting, the code is interpreted like:
var bar;
console.log(bar);
bar = "abc";
console.log(bar);
Function Expressions are NOT Hoisted
Beware of the Global Scope
Why “def”? Lets first see what happens. The bar function declaration hoisted to the top of the file followed by var foo. The value of foo is assigned “def” but when bar() is invoked, the value of foo is assigned “def”. Since foo isn’t declared locally within the bar() function, the foo variable here is the same foo variable in the global scope. This is why “def” is printed in the console.
“use-strict”
Declaring “use strict”; at the beginning of the script disallows the assignment of variables before begin declared. By using it, may of these hoisting issues can be avoided.
Related to hoisting is the notion of JavaScript variable scope. The two are related and as you might have already noticed, a misunderstanding about hoisting and scope can lead to some very nasty bugs. But that’s a discussion for another day!
I love to hear any feedback or if there was something something I missed. Leave a comment below!