0 Like

防抖和节流
防抖和节流是 JavaScript 开发中性能优化的重要方案, 下面通过代码教你掌握他们.
防抖
当持续触发事件时,一定时间段内没有再触发事件,事件处理函数才会执行一次,如果设定的时间到来之前,又一次触发了事件,就重新开始延时。
function debounce(fun, delay) {
let timer = null;
return function(args) {
let that = this;
let _args = args;
clearTimeout(timer);
timer = setTimeout(function() {
fun.call(that, _args);
}, delay);
};
}
立即防抖和非立即防抖
非立即执行防抖是触发事件后函数不会立即执行,而是在 n 秒后执行,如果在 n 秒内又触发了事件,则会重新计算函数执行时间。
立即执行防抖是触发事件后函数会立即执行,然后 n 秒内不触发事件才能继续执行函数的效果。
下面是一个综合版的例子。
function debounce(func, wait, immediate) {
var timeout;
return function() {
var context = this;
var args = arguments;
if (timeout) clearTimeout(timeout);
if (immediate) {
var callNow = !timeout;
timeout = setTimeout(function() {
timeout = null;
}, wait);
if (callNow) func.apply(context, args);
} else {
timeout = setTimeout(function() {
func.apply(context, args);
}, wait);
}
};
}
使用场景
search 搜索联想,用户在不断输入值时,用防抖来节约请求资源
window 触发 resize 的时候,不断的调整浏览器窗口大小会不断的触发这个事件,用防抖来让其只触发一次
节流
当持续触发事件时,保证一定时间段内只调用一次事件处理函数。
function throttle(fn, delay) {
let canRun = true;
return function() {
if (!canRun) {
return;
}
canRun = false;
setTimeout(() => {
fn.call(this, arguments);
canRun = true;
}, delay);
};
}
节流分为时间戳版和定时器版,下面是一个综合版。
function throttle(func, delay) {
var timer = null;
var startTime = Date.now();
return function() {
var curTime = Date.now();
var remaining = delay - (curTime - startTime);
var context = this;
var args = arguments;
clearTimeout(timer);
if (remaining <= 0) {
func.apply(context, args);
startTime = Date.now();
} else {
timer = setTimeout(func, remaining);
}
};
}
使用场景
鼠标不断点击触发,mousedown(单位时间内只触发一次)
监听滚动事件,比如是否滑到底部自动加载更多,用 throttle 来判断
参考

PREVIOUS POST
剖析 requestAnimationFrame

NEXT POST
回到顶部的几种玩法