Diego Betto's Blog
Photo by Ellen Qin on Unsplash

June 16, 2024 · 4 min di lettura

Debounce and Throttle in JavaScript: A Simple Guide

Difference and examples between debounce and throttle for events in JavaScript

Condividi:XLinkedInFacebookWhatsApp

Introduction

In JavaScript applications that handle frequent user events, such as resizing the browser or typing into an input field, it’s essential to optimize performance to avoid delays and jank. Debounce and throttle are two common optimization techniques that reduce how often a function runs in response to repeated events. While both aim to improve performance, they work differently and suit different scenarios.

Debounce

Debounce guarantees that a function runs only once for a given period of time, no matter how many times the event fires. This means that if the event fires multiple times in quick succession, the function only runs once, after the specified delay period ends.

Debounce example

Let’s consider a use case where you want to resize an element only after the user has stopped resizing the browser window. Here’s how to implement debounce for this scenario:

function debounce(func, delay) {
  let timeout;
  return function () {
    if (timeout) {
      clearTimeout(timeout);
    }
    timeout = setTimeout(func, delay);
  };
}

const resizeHandler = debounce(() => {
  // Resize the element
}, 250); // 250 millisecond delay

window.addEventListener("resize", resizeHandler);

In this example, the debounce function wraps the function to run, resizeHandler, and introduces a 250 millisecond delay. Every time the resize event fires, the debounce function is called. If the debounce function is called before the delay has elapsed, the existing timer is cleared and a new one is set. As a result, the resizeHandler function only runs once, after the 250 millisecond delay ends, no matter how many times the resize event fired during that period.

Throttle

Throttle limits the maximum number of times a function can run in a given period of time. This means that if the event fires multiple times in quick succession, the function will only run at regular intervals, no matter how many times the event fires in between runs.

Throttle example

Let’s consider a use case where you want to run an API search only once every 500 milliseconds, regardless of how fast the user types. Here’s how to implement throttle for this scenario:

function throttle(func, delay) {
  let lastRun = 0;
  return function () {
    const now = Date.now();
    if (now - lastRun >= delay) {
      func();
      lastRun = now;
    }
  };
}

const searchHandler = throttle(() => {
  // Run the API search
}, 500);

const input = document.getElementById("searchInput");
input.addEventListener("input", searchHandler);

In this example, the throttle function wraps the function to run, searchHandler, and introduces a 500 millisecond delay. Every time the input event fires, the throttle function is called. If the throttle function is called before the delay has elapsed, the run is skipped. If the delay has elapsed instead, the searchHandler function runs and the timestamp of the last run is updated. As a result, the searchHandler function can run at most once every 500 milliseconds, no matter how fast the user types.

This comes in handy, for example, if you have autocomplete fields and don’t want to send too many requests to the backend.

Test code

I put together a small example to show you the difference between debounce and throttle when handling repeated click events.
Try clicking quickly and for more than 1 second on the gray divs and watch when they light up.

See the Pen Debounce vs Throttle by Diego Betto (@bettodiego) on CodePen.

Conclusion

Debounce and throttle are valuable tools for optimizing the performance of JavaScript applications that handle frequent user events.

The choice between debounce and throttle depends on the specific scenario.

  • If it’s important to guarantee that a function runs only once for a given period of time, use debounce.\
  • If it’s important to limit the maximum number of times a function can run in a given period of time, use throttle.

It’s not just a matter of style: an event handler running unchecked on every scroll or resize is one of the most common ways to drive up your site’s INP. I go into it with real numbers in the article on Core Web Vitals.

Happy coding! 🙂

Condividi:XLinkedInFacebookWhatsApp