That's Hoisting in JavaScript.
Hoisting is a JavaScript mechanism where the JavaScript interpreter moves all variable and function declarations to the top of the current scope before the code execution starts.
Because of this, we're able to access these functions and variables before their declaration.
Scenarios of hoisting in JavaScript:
Although JavaScript is an interpreted language, it still gets all the declarations stored in memory, before it starts executing the code.
This task is accomplished by the JavaScript interpreter. How?
The JavaScript interpreter runs through the entire code, twice.
Hence, there are two phases in JavaScript code execution:
function wrapper() {
console.log({bottom})
var bottom = 100
}
wrapper()
// { bottom: undefined }
var hoisting:
var variables are hoisted (lifted to the top of the scope), and initialised with a value of undefined,
function checkVarHoisting(){
console.log({custom}) // undefined
var custom = 100;
console.log({custom}) // 100
}
checkVarHoisting()
// Step 1
// Hoisting phase - First Run
function checkVarHoisting(){
var custom = undefined
// console.log({custom})
// console.log({custom})
}
checkVarHoisting()
// Step 2
// Execution phase - Second Run
function checkVarHoisting(){
var custom = undefined
console.log({custom}) // undefined
custom = 100
console.log({custom}) // 100
}
checkVarHoisting()
function checkVarHoisting(){
// Reference Error: Cannot access
// before initialisation
console.log({custom})
let custom = 100;
}
checkVarHoisting()
let and const hoisting:
// Reference Error: not defined
console.log({custom})
let custom = 100;
function checkVarHoisting(){
for (let i = 0; i < 10; i += 1){
console.log({i})
}
console.log({custom})
let custom = 100;
}
checkVarHoisting()
/**
* Line 2 - 6 is TDZ
* for variable "custom"
* If "custom" is accessed
* before line 7, it gives
* Reference Error: cannot
* access before initialisation
*/
TDZ - Temporal Dead Zone
function checkVarHoisting(){
for (let i = 0; i < 10; i += 1){
console.log({i})
}
function inner() {
// ReferenceError:
// Cannot access
// 'custom' before initialization
console.log("inside", {custom})
let custom = 100;
}
inner()
}
checkVarHoisting()
TDZ - Temporal Dead Zone
function checkVarHoisting(){
for (let i = 0; i < 10; i += 1){
console.log({i})
}
// ReferenceError:
// 'custom' is not defined
console.log("inside", {custom})
function inner() {
let custom = 100;
}
inner()
}
checkVarHoisting()
func123()
func246()
function func123(){
for (let i = 0; i < 10; i += 1){
console.log({i})
}
console.log({custom})
let custom = 100;
}
function func246() {
console.log({"func246"})
}
Function Declaration Hoisting
Function declarations are hoisted to the top of their current scope.
They are hoisted along with their definitions, so they can be called in the code before their declaration
var
- hoisted (initialised with undefined)let and const
- hoisted (not initialised, TDZ - temporal dead zone)variables inside functions
- hoisted like abovefunction declaration
- hoisted to the of the scope, with definitionfunction expression
- Not hoisted
arrow functions
- Not hoisted
class declaration
- Not hoistedclass methods
- Not hoisted