READMEJavaScript

README

Module 04 Control Flow / .3 For Loops

Concept Lesson
Intermediate
4 min

Learning Objective

Understand Module 04 Control Flow well enough to explain it, recognize it in JavaScript, and apply it in a small task.

Why It Matters

This concept is part of the foundation that later lessons and projects assume you already understand.

ControlFlowTable Of ContentsBasic SyntaxSimple Example
Private notes
0/8000

Notes stay private to your browser until account sync is configured.

README
2 min read18 headings

4.3 For Loops

Overview

The for loop is the most common looping structure in JavaScript. It executes a block of code a specified number of times, with built-in control over initialization, condition checking, and iteration updates.


Table of Contents

  1. Basic Syntax
  2. How For Loops Work
  3. Loop Components
  4. Iterating Arrays
  5. Nested Loops
  6. Loop Control: break and continue
  7. Common Patterns
  8. Variations
  9. Performance Considerations
  10. Best Practices

Basic Syntax

for (initialization; condition; update) {
  // code to execute each iteration
}

Simple Example

for (let i = 0; i < 5; i++) {
  console.log(i);
}
// Output: 0, 1, 2, 3, 4

Components Breakdown

ComponentPurposeExample
initializationRuns once before loop startslet i = 0
conditionChecked before each iterationi < 5
updateRuns after each iterationi++

How For Loops Work

    β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
    β”‚  1. Initialization  β”‚  ◄─── Runs once at start
    β”‚     (let i = 0)     β”‚
    β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜
               β”‚
    β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β–Όβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
    β”‚   2. Check          β”‚
    β”‚   Condition         β”‚
    β”‚   (i < 5)           β”‚
    β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜
               β”‚
       β”Œβ”€β”€β”€β”€β”€β”€β”€β”΄β”€β”€β”€β”€β”€β”€β”€β”
       β”‚               β”‚
    [true]          [false]
       β”‚               β”‚
       β–Ό               β–Ό
    β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”    Exit Loop
    β”‚ 3. Executeβ”‚
    β”‚ Loop Body β”‚
    β””β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”˜
          β”‚
    β”Œβ”€β”€β”€β”€β”€β–Όβ”€β”€β”€β”€β”
    β”‚ 4. Updateβ”‚
    β”‚  (i++)   β”‚
    β””β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”˜
          β”‚
          └───────────────────┐
                              β”‚
               β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β–Ό
               β”‚ Go back to Step 2

Step-by-Step Execution

for (let i = 0; i < 3; i++) {
  console.log(`Iteration ${i}`);
}

// Step 1: Initialize i = 0
// Step 2: Check 0 < 3? Yes
// Step 3: Execute body: log "Iteration 0"
// Step 4: Update i to 1

// Step 2: Check 1 < 3? Yes
// Step 3: Execute body: log "Iteration 1"
// Step 4: Update i to 2

// Step 2: Check 2 < 3? Yes
// Step 3: Execute body: log "Iteration 2"
// Step 4: Update i to 3

// Step 2: Check 3 < 3? No
// Exit loop

Loop Components

Initialization

// Single variable
for (let i = 0; i < 5; i++) {}

// Multiple variables
for (let i = 0, j = 10; i < j; i++, j--) {
  console.log(`i=${i}, j=${j}`);
}
// i=0, j=10
// i=1, j=9
// ... until i >= j

// Using existing variable
let k = 0;
for (; k < 5; k++) {
  console.log(k);
}

Condition

// Simple comparison
for (let i = 0; i < 10; i++) {}

// Complex condition
for (let i = 0; i < 10 && i !== 5; i++) {}

// Function call (evaluated each iteration)
for (let i = 0; i < arr.length; i++) {}

// Omitted condition = infinite loop
for (let i = 0; ; i++) {
  if (i >= 5) break; // Must have break!
}

Update Expression

// Increment by 1
for (let i = 0; i < 10; i++) {}

// Increment by 2
for (let i = 0; i < 10; i += 2) {}
// 0, 2, 4, 6, 8

// Decrement
for (let i = 10; i > 0; i--) {}
// 10, 9, 8, ..., 1

// Multiply
for (let i = 1; i <= 1000; i *= 2) {}
// 1, 2, 4, 8, 16, 32, 64, 128, 256, 512

// Multiple updates
for (let i = 0, j = 5; i < j; i++, j--) {}

Iterating Arrays

Basic Array Iteration

const fruits = ['apple', 'banana', 'cherry'];

for (let i = 0; i < fruits.length; i++) {
  console.log(`${i}: ${fruits[i]}`);
}
// 0: apple
// 1: banana
// 2: cherry

Optimized Array Iteration

// Cache the length (slightly faster for large arrays)
const arr = [1, 2, 3, 4, 5];

for (let i = 0, len = arr.length; i < len; i++) {
  console.log(arr[i]);
}

Reverse Iteration

const arr = ['a', 'b', 'c', 'd'];

for (let i = arr.length - 1; i >= 0; i--) {
  console.log(arr[i]);
}
// d, c, b, a

Modifying Array During Iteration

// Doubling values in place
const numbers = [1, 2, 3, 4, 5];

for (let i = 0; i < numbers.length; i++) {
  numbers[i] = numbers[i] * 2;
}
console.log(numbers); // [2, 4, 6, 8, 10]

Nested Loops

// 2D iteration
for (let i = 0; i < 3; i++) {
  for (let j = 0; j < 3; j++) {
    console.log(`(${i}, ${j})`);
  }
}
// (0,0), (0,1), (0,2), (1,0), (1,1), (1,2), (2,0), (2,1), (2,2)

Multiplication Table

for (let i = 1; i <= 5; i++) {
  let row = '';
  for (let j = 1; j <= 5; j++) {
    row += (i * j).toString().padStart(4);
  }
  console.log(row);
}
/*
   1   2   3   4   5
   2   4   6   8  10
   3   6   9  12  15
   4   8  12  16  20
   5  10  15  20  25
*/

2D Array Traversal

const matrix = [
  [1, 2, 3],
  [4, 5, 6],
  [7, 8, 9],
];

for (let row = 0; row < matrix.length; row++) {
  for (let col = 0; col < matrix[row].length; col++) {
    console.log(`matrix[${row}][${col}] = ${matrix[row][col]}`);
  }
}

Loop Control: break and continue

break - Exit Loop Immediately

for (let i = 0; i < 10; i++) {
  if (i === 5) {
    break; // Exit the loop
  }
  console.log(i);
}
// Output: 0, 1, 2, 3, 4

continue - Skip Current Iteration

for (let i = 0; i < 10; i++) {
  if (i % 2 === 0) {
    continue; // Skip even numbers
  }
  console.log(i);
}
// Output: 1, 3, 5, 7, 9

Labeled Statements for Nested Loops

outer: for (let i = 0; i < 3; i++) {
  for (let j = 0; j < 3; j++) {
    if (i === 1 && j === 1) {
      break outer; // Breaks out of both loops
    }
    console.log(`(${i}, ${j})`);
  }
}
// (0,0), (0,1), (0,2), (1,0)
// Stops at (1,1)

Common Patterns

Sum of Array

const numbers = [1, 2, 3, 4, 5];
let sum = 0;

for (let i = 0; i < numbers.length; i++) {
  sum += numbers[i];
}
console.log(sum); // 15

Find Element

const users = [
  { id: 1, name: 'Alice' },
  { id: 2, name: 'Bob' },
  { id: 3, name: 'Charlie' },
];

function findById(arr, id) {
  for (let i = 0; i < arr.length; i++) {
    if (arr[i].id === id) {
      return arr[i];
    }
  }
  return null;
}

console.log(findById(users, 2)); // { id: 2, name: "Bob" }

Count Occurrences

const text = 'hello world';
let count = 0;

for (let i = 0; i < text.length; i++) {
  if (text[i] === 'l') {
    count++;
  }
}
console.log(count); // 3

Build New Array

const numbers = [1, 2, 3, 4, 5];
const squared = [];

for (let i = 0; i < numbers.length; i++) {
  squared.push(numbers[i] ** 2);
}
console.log(squared); // [1, 4, 9, 16, 25]

Filter Elements

const numbers = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
const evens = [];

for (let i = 0; i < numbers.length; i++) {
  if (numbers[i] % 2 === 0) {
    evens.push(numbers[i]);
  }
}
console.log(evens); // [2, 4, 6, 8, 10]

String Manipulation

const str = 'Hello';
let reversed = '';

for (let i = str.length - 1; i >= 0; i--) {
  reversed += str[i];
}
console.log(reversed); // "olleH"

Variations

Omitting Parts

// Omit initialization
let i = 0;
for (; i < 5; i++) {
  console.log(i);
}

// Omit update
for (let i = 0; i < 5; ) {
  console.log(i);
  i++; // Update inside body
}

// Infinite loop (omit condition)
for (;;) {
  // Must use break to exit!
  break;
}

for...of Loop (Arrays)

const fruits = ['apple', 'banana', 'cherry'];

// Traditional for loop
for (let i = 0; i < fruits.length; i++) {
  console.log(fruits[i]);
}

// for...of (cleaner for iteration)
for (const fruit of fruits) {
  console.log(fruit);
}

for...in Loop (Objects)

const person = { name: 'John', age: 30, city: 'NYC' };

for (const key in person) {
  console.log(`${key}: ${person[key]}`);
}
// name: John
// age: 30
// city: NYC

Performance Considerations

Cache Array Length

// Slower (length recalculated each iteration)
for (let i = 0; i < largeArray.length; i++) {}

// Faster (length cached)
for (let i = 0, len = largeArray.length; i < len; i++) {}

Avoid Expensive Operations in Condition

// ❌ Bad: DOM query every iteration
for (let i = 0; i < document.querySelectorAll('.item').length; i++) {}

// βœ… Good: Cache the result
const items = document.querySelectorAll('.item');
for (let i = 0; i < items.length; i++) {}

Use Local Variables

// Access array element once per iteration
for (let i = 0; i < items.length; i++) {
  const item = items[i]; // Cache reference
  console.log(item.name, item.value, item.type);
}

Best Practices

1. Use Meaningful Variable Names

// ❌ Confusing
for (let x = 0; x < users.length; x++) {
  console.log(users[x].name);
}

// βœ… Clear (when index is needed)
for (let userIndex = 0; userIndex < users.length; userIndex++) {
  console.log(users[userIndex].name);
}

// βœ… Better: Use for...of when index isn't needed
for (const user of users) {
  console.log(user.name);
}

2. Use let, Not var

// ❌ var has function scope (can cause issues)
for (var i = 0; i < 3; i++) {
  setTimeout(() => console.log(i), 100);
}
// Logs: 3, 3, 3

// βœ… let has block scope
for (let i = 0; i < 3; i++) {
  setTimeout(() => console.log(i), 100);
}
// Logs: 0, 1, 2

3. Keep Loop Body Simple

// ❌ Complex loop body
for (let i = 0; i < data.length; i++) {
  // 50 lines of code...
}

// βœ… Extract to function
for (let i = 0; i < data.length; i++) {
  processItem(data[i]);
}

function processItem(item) {
  // Processing logic here
}

4. Use Array Methods When Appropriate

// For loop
const doubled = [];
for (let i = 0; i < numbers.length; i++) {
  doubled.push(numbers[i] * 2);
}

// Array method (often cleaner)
const doubled = numbers.map((n) => n * 2);

Summary

FeatureDescription
InitializationRuns once before loop
ConditionChecked before each iteration
UpdateRuns after each iteration
breakExits loop immediately
continueSkips to next iteration
LabelsControl nested loops

Common Uses

  • Iterating arrays with index access
  • Counting and accumulating
  • Nested iterations (2D arrays)
  • Building new arrays/strings
  • Finding/filtering elements

Next Steps

  • Practice with the examples in examples.js
  • Complete the exercises in exercises.js
  • Learn about while and do...while loops
  • Explore for...of and for...in loops

Skill Check

Test this lesson

Answer 4 quick questions to lock in the lesson and feed your adaptive practice queue.

--
Score
0/4
Answered
Not attempted
Status
1

Which module does this lesson belong to?

2

Which section is covered in this lesson content?

3

Which term is most central to this lesson?

4

What is the best way to use this lesson for real learning?

Your answers save locally first, then sync when account storage is available.
Practice queue