Skip to content
elephantoo

Loops

Lesson 6 of 34 13 min read

for, while, do…while, for…of, for…in, break and continue.


Loops repeat code: print a times table, add up a shopping cart, process every row of data. JavaScript has several loops, each suited to a different job.

The classic for loop#

JavaScript
for (let i = 1; i <= 5; i++) {
  console.log(`Step ${i}`);
}
Output
Step 1
Step 2
Step 3
Step 4
Step 5

The three parts inside the parentheses are:

  1. Initialiser — let i = 1 runs once before the loop.
  2. Condition — i <= 5 is checked before each iteration; the loop stops when it's falsy.
  3. Update — i++ runs after each iteration.

Use let (not const) for the counter, since it changes. Counting down or in steps works the same way:

JavaScript
for (let i = 10; i > 0; i -= 3) {
  console.log(i);
}
// 10, 7, 4, 1

Looping over an array by index

JavaScript
const lessons = ["Intro", "Variables", "Loops"];
for (let i = 0; i < lessons.length; i++) {
  console.log(`${i + 1}. ${lessons[i]}`);
}
Output
1. Intro
2. Variables
3. Loops

Note i < lessons.length, not <=. Arrays start at index 0, so the last index is length - 1. Getting this wrong is the famous off-by-one error.

for...of: loop over values#

When you don't need the index, for...of is cleaner. It works with arrays, strings, Maps, Sets and anything iterable:

JavaScript
const prices = [199, 499, 99];
let total = 0;
for (const price of prices) {
  total += price;
}
console.log(total); // 797

for (const char of "hey") {
  console.log(char); // h, e, y (one per line)
}

Need the index too? Use entries() with destructuring:

JavaScript
const colours = ["red", "green", "blue"];
for (const [index, colour] of colours.entries()) {
  console.log(index, colour);
}
Output
0 red
1 green
2 blue

for...in: loop over object keys#

JavaScript
const scores = { ada: 91, grace: 87, alan: 78 };
for (const name in scores) {
  console.log(`${name}: ${scores[name]}`);
}
Output
ada: 91
grace: 87
alan: 78

Don't use for...in on arrays. It iterates keys as strings ("0", "1"…) and can include inherited properties. For objects, many developers prefer for (const [key, value] of Object.entries(obj)), which you'll see in the objects lessons.

while: loop until something changes#

Use while when you don't know in advance how many iterations you need:

JavaScript
let balance = 1000;
let years = 0;
while (balance < 2000) {
  balance *= 1.08; // 8% growth per year
  years++;
}
console.log(`Doubled after ${years} years: ₹${balance.toFixed(2)}`);
Output
Doubled after 10 years: ₹2158.92

Make sure something inside the loop eventually makes the condition false — otherwise you've written an infinite loop and the page or process will freeze.

do...while: run at least once#

JavaScript
let attempts = 0;
let roll;
do {
  roll = Math.floor(Math.random() * 6) + 1; // 1–6
  attempts++;
} while (roll !== 6);
console.log(`Rolled a 6 after ${attempts} attempt(s)`);

The body runs first, then the condition is checked — ideal for "try, then check" logic like retrying input.

break and continue#

JavaScript
const numbers = [4, 7, -1, 12, 3];

for (const n of numbers) {
  if (n < 0) {
    console.log("Found a negative number, stopping.");
    break; // leave the loop entirely
  }
  console.log(n);
}
Output
4
7
Found a negative number, stopping.
JavaScript
for (let i = 1; i <= 10; i++) {
  if (i % 2 === 0) continue; // skip even numbers
  console.log(i);
}
// 1, 3, 5, 7, 9

Breaking out of nested loops with labels

JavaScript
const grid = [
  [1, 2, 3],
  [4, 99, 6],
  [7, 8, 9],
];

outer: for (let row = 0; row < grid.length; row++) {
  for (let col = 0; col < grid[row].length; col++) {
    if (grid[row][col] === 99) {
      console.log(`Found 99 at row ${row}, col ${col}`);
      break outer; // exits both loops
    }
  }
}
Output
Found 99 at row 1, col 1

Labels are rare; often it's cleaner to move the loops into a function and return.

Nested loops: a times table#

JavaScript
for (let a = 1; a <= 3; a++) {
  let row = "";
  for (let b = 1; b <= 3; b++) {
    row += String(a * b).padStart(4);
  }
  console.log(row);
}
Output
   1   2   3
   2   4   6
   3   6   9

Loops vs array methods#

For arrays, you'll often use methods like forEach, map, filter and reduce instead of hand-written loops:

JavaScript
const cart = [199, 499, 99];
const total = cart.reduce((sum, p) => sum + p, 0);
const expensive = cart.filter((p) => p > 150);
console.log(total, expensive); // 797 [ 199, 499 ]

These are covered in Array methods. Plain loops are still the right tool when you need break, await inside the loop, or maximum performance.

Which loop should I use?#

SituationLoop
Values of an array/string/Setfor...of
Need the indexfor or for...of with .entries()
Keys of a plain objectfor...of Object.entries(obj) or for...in
Unknown number of iterationswhile
Must run at least oncedo...while

Common mistakes#

  • Off-by-one: i <= arr.length reads past the end (giving undefined).
  • Infinite loops: forgetting to update the variable in a while.
  • Using for...in on an array.
  • Using var i in loops that create callbacks — every callback sees the final value. let creates a fresh i per iteration (you'll see why in Scope & closures).

What's next#

You can now repeat work. Next, you'll package logic into reusable functions.

Check your understanding

Quick quiz

0/3 answered
  1. 1.Which loop is the best fit for going through the *values* of an array?

  2. 2.How many times does do { n++; } while (false); run its body?

  3. 3.What does continue do inside a loop?

Finished reading?

Mark this lesson complete to track your progress.