Lesson 5 12 min

Common Bug Patterns

Recognize the most common bug patterns — off-by-one errors, null references, race conditions, async issues, and type mismatches — to identify bugs faster.

🔄 Recall Bridge: In the previous lesson, you learned debugging tools — print statements, IDE debuggers, and browser DevTools. Now let’s build your pattern recognition: the common bug types that cause 80% of all bugs.

Experienced developers debug faster because they’ve seen the same bug patterns hundreds of times. When they see “index out of bounds,” they immediately check loop boundaries (off-by-one). When results are intermittent, they look for race conditions. Pattern recognition turns 30-minute investigations into 30-second diagnoses.

The Top Bug Patterns

Pattern 1: Off-by-One Errors

Symptoms: Array index out of bounds, missing first/last element, extra iteration

VariantWrongCorrect
Loop boundaryi <= array.lengthi < array.length
Start indexfor i in range(1, n)for i in range(0, n)
Slice endstr.slice(0, str.length - 1)Depends on intent
Paginationpage 1 = items 1-10page 1 = items 0-9 (or 1-10?)

Pattern 2: Null/Undefined References

Symptoms: “Cannot read property of null/undefined,” NullPointerException

Common causes:

CauseExamplePrevention
API returns nulluser.profile.avatar when profile is nullOptional chaining: user?.profile?.avatar
Missing function parameterfunction greet(name) { name.toUpperCase() } called without argsDefault parameters or null checks
Uninitialized variableUsing result before async call finishesInitialize with default value
Wrong property namedata.username when the field is data.user_nameCheck actual API response shape

Pattern 3: Race Conditions

Symptoms: Works sometimes, fails intermittently, logging makes it “disappear”

AI prompt for race condition diagnosis:

My code calls [OPERATION A] and [OPERATION B] and uses both results. It works 90% of the time but sometimes produces wrong results. Here’s my code: [PASTE]. Is there a race condition? If so, how do I fix it to ensure correct results regardless of execution order?

Pattern 4: Async/Await Errors

Symptoms: Function returns Promise instead of value, undefined result from API call

ErrorCauseFix
Returns [object Promise]Missing awaitAdd await before async call
Undefined resultCallback-based function in async codeWrap in new Promise() or use promisify
Unhandled rejectionMissing .catch() or try/catchWrap async code in try/catch
Sequential instead of parallelAwaiting in a loopUse Promise.all() for independent calls

Pattern 5: Type Mismatches

Symptoms: “1” + 1 = “11” instead of 2, wrong comparison results

IssueCauseFix
String concatenation"5" + 3 === "53"Number("5") + 3 or parseInt("5") + 3
Loose equality"0" == false is trueUse === for strict equality
JSON parsingAPI returns string, expected objectJSON.parse(response) if needed
Boolean coercionif ("false") is trueCompare explicitly: if (value === "true")

Pattern 6: State Mutation Bugs

Symptoms: Value changed “mysteriously,” function has side effects

Common cause: Modifying a shared object/array instead of creating a copy.

Quick Check: Your search function returns results for the previous query, not the current one. The user types “hello,” results show for “hell.” What pattern is this? (Answer: A stale closure or debounce timing issue. The search handler captures the old query value. Either: (1) The debounce fires with the old value (fix: use the latest value, not the captured one), or (2) An older API response arrives after a newer one (fix: cancel or ignore stale responses using an abort controller or request ID).)

AI for Pattern Recognition

AI prompt when you’re stuck:

I have a bug with these symptoms: [DESCRIBE]. Which of these common bug patterns does this match: off-by-one, null reference, race condition, async error, type mismatch, state mutation, stale closure, or something else? For the matched pattern, suggest the most likely cause and fix.

Key Takeaways

  • Off-by-one errors and null references are the two most common bug patterns — when you see “index out of bounds” check loop boundaries, when you see “cannot read property of null” trace backward to find where the null value originated
  • Race conditions are identifiable by their symptoms: works in development but fails intermittently in production, and adding logging makes the problem disappear (because logging changes execution timing) — fix by never assuming async operations complete in a specific order
  • Build a mental library of bug patterns: when you encounter a bug, match its symptoms to known patterns first — experienced developers debug 40-60% faster because they recognize patterns instead of investigating from scratch every time

Up Next

In the next lesson, you’ll learn to debug production issues — where you can’t attach a debugger, can’t add print statements, and must investigate through logs, monitoring, and error tracking.

Knowledge Check

1. You have an array of 10 items (indices 0-9). Your loop uses `for (let i = 0; i <= 10; i++)`. The code crashes on the last iteration. What bug pattern is this?

2. Your app works perfectly in development but in production, a feature that reads data from two API calls sometimes shows wrong results. When you add logging, the problem seems to disappear. What bug pattern is this?

3. A function works correctly 99% of the time. It only fails when the input is an empty string: `""`. Your code checks `if (input)` to validate the input. What's the bug pattern?

Answer all questions to check

Complete the quiz above first

Related Skills