一、核心概念对比
维度 | 防抖(Debounce) | 节流(Throttle) |
---|---|---|
定义 | 事件触发后,等待固定时间再执行回调;若期间再次触发,则重新计时。 | 事件触发后,固定时间内只执行一次回调,后续触发被忽略。 |
目标 | 确保高频事件(如输入)的最终结果只触发一次。 | 确保高频事件(如滚动)按固定频率执行。 |
执行时机 | 最后一次触发后的等待时间结束时执行。 | 按固定时间间隔执行(如每秒一次)。 |
类比 | 电梯关门:有人进出时重新计时关门。 | 水龙头滴水:无论拧多快,水滴按固定频率落下。 |
二、代码实现
1. 防抖(Debounce)
javascript
function debounce(fn, delay) {
let timer = null;
return function(...args) {
clearTimeout(timer); // 清除之前的计时
timer = setTimeout(() => {
fn.apply(this, args); // 延迟执行
}, delay);
};
}
// 示例:输入框搜索建议
const searchInput = document.getElementById('search');
searchInput.addEventListener('input', debounce(function(e) {
console.log('发起搜索请求:', e.target.value);
}, 500));
2. 节流(Throttle)
javascript
function throttle(fn, interval) {
let lastTime = 0;
return function(...args) {
const now = Date.now();
if (now - lastTime >= interval) { // 判断是否达到时间间隔
fn.apply(this, args);
lastTime = now;
}
};
}
// 示例:滚动加载更多
window.addEventListener('scroll', throttle(function() {
console.log('检查滚动位置,加载数据...');
}, 1000));
三、使用场景
场景 | 防抖(Debounce) | 节流(Throttle) |
---|---|---|
输入框实时搜索 | ✅ 用户停止输入后发起请求(如500ms无输入) | ❌ 不适合(输入期间仍需响应) |
窗口调整(resize) | ✅ 调整结束后计算布局 | ✅ 按固定频率更新布局(如每秒一次) |
按钮防重复点击 | ✅ 避免用户快速点击多次提交 | ✅ 固定时间内只允许提交一次 |
滚动事件(scroll) | ❌ 最后一次滚动后触发可能不符合预期 | ✅ 滚动期间定期检查位置(如触底加载) |
鼠标移动(mousemove) | ❌ 需要连续响应时不适用 | ✅ 限制高频更新(如拖拽元素时降低渲染频率) |
四、高频面试问题
1. 如何手写防抖和节流?
- 参考上述代码实现,注意闭包和
apply
绑定上下文。
2. 防抖和节流的本质区别是什么?
- 防抖关注"最后一次触发后的结果",节流关注"固定间隔内的执行频率"。
3. 如何选择防抖或节流?
- 防抖:适合结果导向型场景(如搜索建议、提交按钮)。
- 节流:适合过程控制型场景(如滚动加载、实时定位)。
4. 防抖的立即执行版本如何实现?
-
添加参数控制是否立即执行第一次触发:
javascriptfunction debounce(fn, delay, immediate) { let timer = null; return function(...args) { if (immediate && !timer) { fn.apply(this, args); // 立即执行 } clearTimeout(timer); timer = setTimeout(() => { if (!immediate) fn.apply(this, args); timer = null; }, delay); }; }
五、常见误区
- 过度依赖第三方库 :虽然Lodash的
_.debounce
和_.throttle
功能完善,但面试需掌握原生实现。 - 忽视this和参数绑定 :回调函数中需正确传递
this
和事件参数(如event
)。 - 时间间隔设置不合理:防抖的延迟过长会导致响应迟钝,节流的间隔过短会失去优化意义。
六、总结回答技巧
- 一句话概括 :
"防抖是延迟执行,确保连续触发只执行最后一次;节流是限频执行,确保连续触发按固定频率执行。" - 结合项目举例 :
"在商品搜索页中,输入框用防抖减少请求次数;图片懒加载用节流控制滚动检查频率。" - 扩展思考 :
"防抖和节流本质是闭包的应用,通过控制计时器和时间戳管理事件触发逻辑。"