yanyue404/blog

节流与防抖如何区分?

Opened this issue · 0 comments

前言

防抖与节流都是用来处理事件频发的问题。但是在很多情况下不知道该使用哪一个,此篇文章记录下来我的使用心得。

throttle

节流,强调时间间隔,固定的间隙,一段时间只执行第一次,n 秒后才可执行下一次。

常见应用场景:按钮点击频发、滚动条事件。

当一个提交订单的按钮被用户一秒钟点击五次,一下子创建了五个订单,再比如领取优惠券,面对用户无恶意的疯狂点击。这些场景我们需要在一段时间拦截用户的点击操作,不执行响应的函数。

<button>领取优惠券</button>
// 时间戳版本
function throttle(fn, wait = 1500) {
  let _lastTime = null;
  return function () {
    let _nowTime = +new Date();
    if (_nowTime - _lastTime > wait || !_lastTime) {
      fn.apply(this, arguments);
      _lastTime = _nowTime;
    }
  };
}

document.querySelector("button").onclick = throttle(function (e) {
  console.log("领取优惠券成功");
}, 1000);

debounce

防抖,没有固定的时间间隙,在事件被触发 n 秒后再执行回调函数,并且如果在这 n 秒内事件被重新触发,则重新计时,只关心最后一次的有效操作。

常见应用场景:输入框的 keyup 事件,window 的 resize、鼠标移动 事件等。

用户在键盘上输入需要实时的 ajax 请求搜索的内容,在用户多次输入超过一个间隔时间之后才响应当前输入的关键词,去执行搜索请求,而当用户保持匀速的输入状态时,我们则推迟请求的时间。(公交车乘客上车,车门一段时间自动关闭)

<input type="text" placeholder="请输入搜索关键字" />
function debounce(func, wait) {
  let timeout;
  return function () {
    const context = this;
    const args = arguments;
    if (timeout) clearTimeout(timeout);
    timeout = setTimeout(() => {
      func.apply(context, args);
    }, wait);
  };
}

document.querySelector("input").onkeyup = debounce(function (e) {
  console.log("拿到关键词了:" + e.target.value + ", 快去搜索吧");
}, 500);

参考