JavaScript · Intermediate

JavaScript switch vs if / else: choose by the shape of the decision

A practical comparison of switch and if / else in JavaScript, including strict matching, fall-through, ranges, declarations, and lookup objects.

Updated · 652 words · 3 min read

switch and if / else can often express the same outcome, but they make different decision shapes easy to see. Choose based on what is being compared, not on a rule about how many branches are “too many.”

Use switch for exact values of one expression

A switch evaluates its expression once and finds a matching case using strict equality semantics:

function statusMessage(status) {
  switch (status) {
    case 'draft':
      return 'Keep working';
    case 'review':
      return 'Waiting for review';
    case 'published':
      return 'Live';
    default:
      return 'Unknown status';
  }
}

The repeated idea—“compare status with this exact value”—is visible without repeating status === on every line.

An equivalent chain is valid, just more repetitive:

if (status === 'draft') {
  return 'Keep working';
} else if (status === 'review') {
  return 'Waiting for review';
} else if (status === 'published') {
  return 'Live';
}

return 'Unknown status';

Use if for ranges and different questions

A branch chain becomes clearer when each condition asks something different:

if (account.isSuspended) {
  denyAccess();
} else if (account.plan === 'team' && account.seats > 0) {
  allowTeamAccess();
} else if (trialDaysRemaining > 0) {
  allowTrialAccess();
} else {
  showUpgrade();
}

Forcing those expressions into case labels would hide the decision behind a switch (true) pattern:

switch (true) {
  case account.isSuspended:
    denyAccess();
    break;
  case account.plan === 'team' && account.seats > 0:
    allowTeamAccess();
    break;
}

This works because each case expression is compared with true, but ordinary if statements communicate boolean branching more directly.

Ranges are another natural fit for if:

if (score >= 90) {
  grade = 'A';
} else if (score >= 80) {
  grade = 'B';
} else {
  grade = 'C or below';
}

A switch matches strictly

Case selection does not loosely coerce strings and numbers:

const value = '1';

switch (value) {
  case 1:
    console.log('number');
    break;
  case '1':
    console.log('string'); // runs
    break;
}

That is usually desirable. Normalise external input before switching when several representations should mean the same thing.

Fall-through is both a feature and a trap

After a matching case, JavaScript continues into following cases until it reaches break, return, throw, or the end of the statement.

switch (role) {
  case 'owner':
    permissions.push('delete');
    // falls through intentionally
  case 'editor':
    permissions.push('edit');
    // falls through intentionally
  case 'viewer':
    permissions.push('read');
}

This can model cumulative permissions, but an omitted break often creates a bug. Comment intentional fall-through and consider whether explicit data would be easier to maintain.

Cases can share one body without fall-through behaviour inside the body:

switch (extension) {
  case 'jpg':
  case 'jpeg':
  case 'png':
    return 'image';
  default:
    return 'other';
}

Put case declarations inside braces

The cases of one switch share a lexical scope. Repeating a const name across cases can cause a syntax error even though only one case runs:

switch (action) {
  case 'create': {
    const message = 'Created';
    log(message);
    break;
  }
  case 'update': {
    const message = 'Updated';
    log(message);
    break;
  }
}

The extra braces give each case its own block scope.

Sometimes neither is the best representation

When exact keys only map to values, store the mapping as data:

const labels = {
  draft: 'Keep working',
  review: 'Waiting for review',
  published: 'Live',
};

const message = labels[status] ?? 'Unknown status';

This avoids control flow entirely, makes the valid keys visible, and is easy to extend. Use Map when keys are not strings or when you want explicit map operations.

A decision checklist

Choose switch when:

  • one expression is compared against exact values;
  • grouping several values into one case improves clarity;
  • case-oriented layout makes the valid states easy to scan.

Choose if / else when:

  • conditions use ranges or inequalities;
  • branches inspect different values;
  • compound boolean logic drives the decision;
  • priority between overlapping conditions matters.

Choose a lookup when cases merely translate keys into values. Performance differences are rarely a useful reason at application scale; clarity and correct behaviour dominate.

See MDN’s switch statement reference for the full grammar and browser behaviour.

Try it visually Open the branch lab

The next useful branch