防抖和节流,清晰解释,看这一篇就够啦
首先要区分一下什么是防抖?,什么是节流?
防抖
当事件触发时,相应的函数不会立即被执行,而是延迟一段时间再执行,并且在这个延迟时间内,如果又触发了,那就再推迟一段时间。什么效果呢?如果频繁的触发,只有最后一次是有效的。
应用场景
- 搜索框搜索输入。只需用户最后一次输入完,再发送请求。
- 窗口大小 resize。只需窗口调整完成后,计算窗口大小。防止重复渲染。
如何实现呢?
- 我们来整理一下思路,首先需要设置一个
Timeout延时,在这个延时到达前,又被触发了,那么就重置一下这个Timeout。那就是说不断的触发就会不断的重置,直到最后,长时间的停止。
// fn 会被防抖函数封装,返回一个真正的防抖函数
function debounce(fn, delay=500) {
let timer = null;
// 注意,返回的这个函数才是一个真正的防抖函数
return function(...args) {
const context = this;
// 重复触发时,重置计时器
if (timer !== null) {
clearTimeout(timer);
}
// 根据 delay 设置延时
timer = setTimeout(() => {
fn.apply(context, args)
}, delay)
}
}
节流
在规定的一段时间内,相应的函数只会被触发一次,即使在这段时间内频繁的触发,也只会有一次生效。
应用场景
- 滚动加载,加载更多或滚到底部监听。
- 搜索框,搜索联想功能。
如何实现呢?
function throttled(fn, delay) {
let timer = null;
let last = Date.now();
return function() {
let now = Date.now();
let remaining = delay - (now - last);
const context = this;
const args = arguments;
clearTimeout(timer);
// 没到规定的时间间隔会一直重置
if (remaining > 0) {
timer = setTimeout(fn, delay);
} else {
last = Date.now();
fn.apply(context, args);
}
}
}