Start with the shape of the decision

Branching code is easier to read when its structure matches the question being asked. Use if when you need to test a condition, switch when you are matching one value against several known cases, and the conditional operator when you need to choose between two expressions. These are guidelines rather than rigid rules: the best choice is the one that lets a reader see the possible paths without tracing unnecessary syntax.

The examples below use standard JavaScript and require no libraries. You can paste each example into a modern browser console or a recent Node.js session. They use small values on purpose, so you can change an input and observe which path runs.

Use if for conditions and ranges

An if statement works well when each branch asks a different question. For example: const score = 74; let result; if (score >= 80) { result = 'strong'; } else if (score >= 60) { result = 'passing'; } else { result = 'retry'; } console.log(result); The conditions are evaluated in order. Because 74 is below 80 but at least 60, this prints 'passing'. The final else makes the remaining outcome explicit.

Order matters when conditions overlap. If score >= 60 appeared first, it would also match scores of 80 or more, preventing the later branch from running. Put more specific checks before broader ones, and consider whether every valid input has a clear outcome. An if statement is also a natural fit when a branch needs several steps, such as validating a value before updating a result.

A short guard can avoid nesting the main path. Inside a function, for instance, if (value == null) { return 'missing'; } handles null or undefined before the rest of the function continues. Use that loose comparison deliberately: == null matches both null and undefined. For most other comparisons, === makes the expected type clearer.

Use switch for several cases of one value

A switch statement can make a list of named cases easy to scan. Try: const status = 'paused'; let label; switch (status) { case 'ready': label = 'Start'; break; case 'paused': label = 'Resume'; break; case 'done': label = 'View result'; break; default: label = 'Unknown status'; } console.log(label); This prints 'Resume'. The default branch gives unexpected values a defined result rather than leaving label unset.

Each case is compared with the switch value using strict matching, so '1' and 1 are different cases. The break statements matter too: without one, execution continues into the next case even if its label does not match. Intentional fall-through is possible, but it can be surprising. If two values should share an outcome, place their case labels together before the shared statements.

Prefer if when the branches depend on ranges, combinations of conditions, or unrelated values. A switch on true can imitate a chain of conditions, but it often hides the simpler question an if would express. Conversely, a long if and else if chain repeatedly comparing the same status to fixed values may be easier to inspect as a switch.

Use the conditional operator for a small choice of values

The conditional operator has the form condition ? valueIfTrue : valueIfFalse. It is an expression, so it fits where a value is needed: const isMember = true; const priceLabel = isMember ? 'Member price' : 'Standard price'; console.log(priceLabel); This prints 'Member price'. Both possible values are visible on one line, making the choice quick to understand.

Keep the two alternatives simple. If either side requires several actions, an if statement is usually clearer. Nested conditional operators can also make it difficult to tell which condition controls which outcome. For example, assigning a label based on three score ranges is often more readable with if and else if, even if a nested expression would be shorter.

Do not confuse the conditional operator with optional chaining or nullish coalescing, which use different syntax and solve different problems. Choose the conditional operator when there are exactly two meaningful outcomes based on a condition, not merely to reduce the number of lines.

Review branches for behavior as well as style

After choosing a form, check its edges. What happens when the value is unexpected, missing, or the wrong type? Does an earlier condition make a later one unreachable? Does every switch case that should stop include a break? Can a reader identify the default outcome? These questions matter more than whether the code uses the fewest characters.

A useful test is to describe the decision aloud: “If this condition holds, do this”; “For this status, use this label”; or “Choose one of these two values.” If the description matches the code’s shape, the branch is likely on the right track. When it does not, rewrite the branch before adding more cases.

Back to category ↗