牛叔叔 的笔记

好好学习

今天 10:09

JavaScript利用防抖(Debounce) 和 节流(Throttle)优化高频率事件处理

牛叔叔

WEB前端

(6)

(0)

收藏

在 JavaScript 中,防抖(Debounce)节流(Throttle) 是两种常用的优化高频率事件处理(如 resizescrollinput 等)的技术。它们都利用了 闭包 的特性来保存状态。


一、防抖(Debounce)

原理:在事件被触发后,等待一段时间(比如 500ms),如果在这段时间内没有再次触发事件,就执行函数;如果再次触发了,则重新计时。

实现(使用闭包):

function debounce(fn, delay) {
  let timer = null;
  return function (...args) {
    // 清除上一次的定时器
    clearTimeout(timer);
    // 设置新的定时器
    timer = setTimeout(() => {
      fn.apply(this, args);
    }, delay);
  };
}

使用示例:

const handleInput = debounce(function (value) {
  console.log('输入内容:', value);
}, 500);

// 模拟频繁输入
handleInput('a');
handleInput('ab');
handleInput('abc'); // 只有最后一次会执行(500ms 后)

二、节流(Throttle)

原理:在一定时间间隔内,最多只执行一次函数。即使事件频繁触发,也保证函数按固定频率执行。

实现(使用闭包 + 时间戳):

function throttle(fn, delay) {
  let lastTime = 0;
  return function (...args) {
    const now = Date.now();
    if (now - lastTime >= delay) {
      fn.apply(this, args);
      lastTime = now;
    }
  };
}

也可以用 setTimeout 实现“延迟执行”的节流,但上述时间戳方式更常用且响应更快。

使用示例:

const handleScroll = throttle(function () {
  console.log('滚动了!');
}, 1000);

// 模拟频繁滚动
window.addEventListener('scroll', handleScroll);

三、对比总结

特性防抖(Debounce)节流(Throttle)
执行时机事件停止触发后执行一次固定时间间隔内最多执行一次
适用场景搜索框输入、窗口 resize滚动加载、按钮点击限制、mousemove
是否立即执行默认延迟后执行(可改造成立即)可控制是否首/尾执行

四、进阶:带 immediate 参数的防抖(立即执行版)

function debounce(fn, delay, immediate = false) {
  let timer = null;
  return function (...args) {
    const callNow = immediate && !timer;
    clearTimeout(timer);
    timer = setTimeout(() => {
      timer = null;
      if (!immediate) fn.apply(this, args);
    }, delay);
    if (callNow) fn.apply(this, args);
  };
}



0条评论

点击登录参与评论