In Jurassic Park, some procedures are prepared before the workday begins - embryo storage is always ready, even before the first scientist arrives. JavaScript has a similar mechanism: hoisting moves certain declarations to the top of their scope before code execution.
Function declarations are fully hoisted - you can call them before they appear in code:
1// This works! The function is hoisted to the top
2sayHello();
3
4function sayHello() {
5 console.log('Hello from Jurassic Park!');
6}
7
8// Also works - hoisting moves the declaration before the call
9const danger = getDangerLevel();
10console.log(danger); // 'HIGH'
11
12function getDangerLevel() {
13 return 'HIGH';
14}1// This DOESN'T work - function expression is not hoisted
2// roar(); // TypeError: roar is not a function
3
4const roar = function() {
5 return 'ROOOAR!';
6};
7
8roar(); // Works here
9
10// Arrow functions also not hoisted
11// checkFence(); // ReferenceError: Cannot access 'checkFence' before initialization
12
13const checkFence = () => 'Fence OK';var declarations are hoisted, but their values are NOT:1console.log(dinoName); // undefined (not ReferenceError!)
2var dinoName = 'Rex';
3console.log(dinoName); // "Rex"
4
5// JavaScript sees it as:
6var dinoName; // declaration hoisted
7console.log(dinoName); // undefined
8dinoName = 'Rex'; // assignment stays in place
9console.log(dinoName); // "Rex"1function checkZone() {
2 console.log(status); // undefined - var hoisted within function
3
4 if (true) {
5 var status = 'CLEAR';
6 }
7
8 console.log(status); // "CLEAR" - var is function-scoped
9}
10
11checkZone();let and const ARE hoisted, but you can't access them before declaration. The period from start of scope to the declaration is called the Temporal Dead Zone (TDZ):1// console.log(raptor); // ReferenceError: Cannot access 'raptor' before initialization
2let raptor = 'Blue';
3console.log(raptor); // "Blue"
4
5// const also has TDZ
6// console.log(danger); // ReferenceError!
7const danger = 'HIGH';1// var can lead to bugs:
2function processData() {
3 console.log(result); // undefined - no error, but that's a bug!
4 // ... 200 lines of code ...
5 var result = computeResult();
6}
7
8// let/const catch errors early:
9function processDataBetter() {
10 // console.log(result); // ReferenceError - clear error message!
11 // ... 200 lines of code ...
12 let result = computeResult();
13}1// Hoisting allows organizing code naturally
2function manageIncident(type, location) {
3 // We can call helper functions before they're defined
4 const severity = calculateSeverity(type);
5 const response = getResponseTeam(severity);
6
7 console.log(`Incident: ${type} at ${location}`);
8 console.log(`Severity: ${severity}`);
9 console.log(`Response team: ${response}`);
10
11 // Helper functions defined after usage - still works!
12 function calculateSeverity(incidentType) {
13 const severityMap = {
14 'ESCAPE': 5,
15 'INJURY': 4,
16 'EQUIPMENT_FAILURE': 3,
17 'MINOR': 1
18 };
19 return severityMap[incidentType] || 2;
20 }
21
22 function getResponseTeam(level) {
23 if (level >= 5) return 'Emergency team + Security';
24 if (level >= 3) return 'Security team';
25 return 'Maintenance';
26 }
27}
28
29manageIncident('ESCAPE', 'Zone A');
30// Incident: ESCAPE at Zone A
31// Severity: 5
32// Response team: Emergency team + SecurityClasses are hoisted like
let/const - they exist in TDZ:1// const dino = new Dinosaur(); // ReferenceError!
2
3class Dinosaur {
4 constructor(name) {
5 this.name = name;
6 }
7}
8
9const dino = new Dinosaur('Rex'); // OK1// 1. Declare variables at the top of their scope
2function goodPractice() {
3 const name = 'Rex';
4 let count = 0;
5 // ... use them below
6}
7
8// 2. Use const by default, let when you need to change the value
9const MAX_DINOSAURS = 100; // never changes
10let currentCount = 0; // changes
11
12// 3. Avoid var - use let/const
13// Bad:
14var oldStyle = 'avoid this';
15// Good:
16const newStyle = 'use this';
17
18// 4. Functions can be defined after their usage
19// (but only function declarations, not expressions)1function checkSecurity() {
2 var fenceStatus = "Offline"; // Hoisted to top of function
3
4 function enableFences() {
5 // This local variable is hoisted to top of enableFences,
6 // but doesn't shadow the outer variable until initialization
7 console.log("Current fence status before change:", fenceStatus); // undefined!
8
9 // Local fenceStatus shadows the one from outer scope
10 var fenceStatus = "Online";
11 console.log("New fence status:", fenceStatus); // "Online"
12 }
13
14 enableFences();
15 console.log("Fence status in main function:", fenceStatus); // "Offline" (unchanged)
16}
17
18checkSecurity();In the above example, the
console.log inside enableFences shows undefined because the local fenceStatus variable is hoisted but not yet initialized, shadowing the variable from the outer scope.1function parkOperations() {
2 // Use const for values that shouldn't change
3 const maxVisitors = 2000;
4
5 // Use let for variables that may change
6 let currentVisitors = 0;
7
8 function admitVisitors(count) {
9 // With let/const, accessing a variable before declaration will throw an error,
10 // making it easier to detect potential problems
11
12 // This would throw an error:
13 // console.log(availableSpace); // ReferenceError
14
15 // Declare first, then use
16 const availableSpace = maxVisitors - currentVisitors;
17 if (count <= availableSpace) {
18 currentVisitors += count;
19 console.log(`Admitted ${count} visitors. Currently in park: ${currentVisitors}`);
20 return true;
21 }
22
23 console.log(`Too many visitors! Available spots: ${availableSpace}`);
24 return false;
25 }
26
27 // Test our function
28 admitVisitors(500); // Admitted 500 visitors
29 admitVisitors(1000); // Admitted 1000 visitors
30 admitVisitors(700); // Too many visitors! Available spots: 500
31
32 return currentVisitors;
33}
34
35console.log(`Total visitors: ${parkOperations()}`);Hoisting is an important concept in JavaScript that affects how code is executed:
undefined initialization - you can reference them, but they'll be undefined before initialization."Hoisting in JavaScript is like morning park setup" - says Dr. Rex. "Before visitors arrive (before code runs), certain preparations are done automatically - protocols are ready, procedures are in place. But the actual data (values) must still be prepared in real time!"