Introduction to Debouncing & Throttling in JavaScript – Optimize Like a Pro
1 . What are Debouncing & Throttling?
2 . Why Do We Need Debouncing & Throttling in JavaScript?
3 . Difference Between Debouncing & Throttling
5 . Basic Example of Throttling
6 . Real-World Use Cases of Debouncing
7 . Real-World Use Cases of Throttling
8 . Debouncing vs Throttling in Search Box
9 . How Debouncing Works Internally
10 . How Throttling Works Internally
11 . Debouncing with Leading & Trailing Options
12 . Throttling with Leading & Trailing Options
13 . Debouncing in React
14 . Throttling in React
15 . Debouncing in Search Suggestions
16 . Throttling in Infinite Scroll
17 . Performance Comparison
18 . Libraries That Provide Debounce & Throttle
19 . Advanced Debounce with Cancel Option
20 . Advanced Throttle with Cancel Option
21 . When to Use Debouncing & Throttling Together
22 . Best Practices
Conclusion
When building interactive web apps, performance is everything. Imagine typing in a search bar and your app making requests on every keystroke, it would slow down drastically. This is where Debouncing & Throttling shine.
Both techniques help in controlling function execution, saving memory, optimizing API calls, and ensuring a smoother user experience in JavaScript.
In this guide, we’ll explore Debouncing & Throttling in JavaScript with explanations, and practical code examples.
Also, if you want to learn more about basics, you can always Reach out JavaScript
Debouncing: Ensures that a function is executed only after a certain delay since the last event.
Throttling: Ensures that a function is executed at most once in a given interval, no matter how many times the event fires.
Example analogy:
Debouncing is like waiting until a person stops talking before you reply.
Throttling is like replying every 5 seconds, no matter how much they talk.
Modern apps deal with:
High-frequency events (scroll, resize, keypress)
Expensive operations (API calls, re-rendering)
Performance bottlenecks
Without optimization, your UI may lag. Debouncing & Throttling help optimize performance.
Feature | Debouncing | Throttling |
---|---|---|
Trigger | Executes after inactivity | Executes at intervals |
Best For | Search inputs, form validation | Scroll, resize, mouse events |
Example | Wait until user stops typing | Update scroll position every 200ms |
function debounce(func, delay) {
let timer;
return function(...args) {
clearTimeout(timer);
timer = setTimeout(() => func.apply(this, args), delay);
};
}
const handleInput = debounce(() => {
console.log("Search API called!");
}, 500);
document.getElementById("search").addEventListener("input", handleInput);
Here, the API fires only after the user stops typing for 500ms.
function throttle(func, limit) {
let lastCall = 0;
return function(...args) {
const now = Date.now();
if (now - lastCall >= limit) {
func.apply(this, args);
lastCall = now;
}
};
}
const handleScroll = throttle(() => {
console.log("Scroll event handled!");
}, 1000);
window.addEventListener("scroll", handleScroll);
Search box API calls
Live form validation
Window resizing adjustments
Auto-saving drafts
Here, scroll events are handled once per second, even if triggered multiple times.
Infinite scrolling
Scroll event animations
Tracking mouse movement
Limiting button clicks
If a user types quickly:
function debounce(func, delay, immediate = false) {
let timer;
return function(...args) {
const callNow = immediate && !timer;
clearTimeout(timer);
timer = setTimeout(() => {
if (!immediate) func.apply(this, args);
timer = null;
}, delay);
if (callNow) func.apply(this, args);
};
}
function throttle(func, limit) {
let lastCall = 0;
let timeout;
return function(...args) {
const now = Date.now();
if (now - lastCall >= limit) {
func.apply(this, args);
lastCall = now;
} else {
clearTimeout(timeout);
timeout = setTimeout(() => {
func.apply(this, args);
lastCall = Date.now();
}, limit - (now - lastCall));
}
};
}
import { useState } from "react";
function App() {
const [query, setQuery] = useState("");
const debounce = (fn, delay) => {
let timer;
return (...args) => {
clearTimeout(timer);
timer = setTimeout(() => fn(...args), delay);
};
};
const handleChange = debounce((e) => {
setQuery(e.target.value);
console.log("API Call: ", e.target.value);
}, 500);
return <input type="text" onChange={handleChange} />;
}
import { useEffect } from "react";
function App() {
const throttle = (fn, limit) => {
let lastCall = 0;
return (...args) => {
const now = Date.now();
if (now - lastCall >= limit) {
fn(...args);
lastCall = now;
}
};
};
useEffect(() => {
const onResize = throttle(() => {
console.log("Resized!");
}, 1000);
window.addEventListener("resize", onResize);
return () => window.removeEventListener("resize", onResize);
}, []);
return <h1>Resize Window</h1>;
}
Debounce saves API costs.
Throttle ensures smooth animations.
Both reduce CPU load.
Lodash → _.debounce, _.throttle
Underscore.js
RxJS (Observables)
function debounceWithCancel(func, delay) {
let timer;
function debounced(...args) {
clearTimeout(timer);
timer = setTimeout(() => func.apply(this, args), delay);
}
debounced.cancel = () => clearTimeout(timer);
return debounced;
}
function throttleWithCancel(func, limit) {
let lastCall = 0;
let timeout;
function throttled(...args) {
const now = Date.now();
if (now - lastCall >= limit) {
func.apply(this, args);
lastCall = now;
} else {
clearTimeout(timeout);
timeout = setTimeout(() => {
func.apply(this, args);
lastCall = Date.now();
}, limit - (now - lastCall));
}
}
throttled.cancel = () => clearTimeout(timeout);
return throttled;
}
Sometimes both are useful:
Use debounce for events where end result matters (search).
Use throttle where continuous updates matter (scroll).
Use libraries like Lodash for reliability.
Debouncing & Throttling in JavaScript are essential optimization techniques that improve user experience, reduce unnecessary executions, and save resources.
Next time you work on search inputs, scroll events, or window resizing, remember:
Debounce → Wait until the action stops.
Throttle → Allow execution at fixed intervals.
Want to explore more? Reach out JavaScript. and boost your skills today.
Software Engineer
Senior Software Engineer