前言
浏览器的 resize、scroll、keypress、mousemove 等事件在触发时,会不断地调用绑定在事件上的回调函数,极大地浪费资源,降低前端性能。为了优化体验,需要对这类事件进行调用次数的限制。
防抖
以用户拖拽改变窗口大小,触发 resize 事件为例,在这过程中窗口的大小一直在改变,所以如果我们在 resize 事件中绑定函数,这个函数将会一直触发,而这种情况大多数情况下是无意义的,还会造成资源的大量浪费。
这时候可以使用函数防抖来优化相关操作:
function debounce(fn, delay = 1000) {
let timer;
return function () {
window.clearTimeout(timer);
timer = setTimeout(() => {
fn.apply(this, arguments);
window.clearTimeout(timer);
}, delay);
}
}
// 进行函数防抖
let debounced = debounce(function () {
console.log('debounce');
});
// 监听resize事件
window.addEventListener('resize', debounced);
先执行 debounce
函数,返回内部函数(实际调用的函数)。
每一次 resize
事件被触发,都会触发返回的内部函数并清除当前的 timer
然后重新设置定时器。
只有在结束触发 resize
事件时,才能在 delay
时间后执计时器内部函数fn。
示意图:
注:在事件触发过程中,只执行一次。
节流
希望连续执行的事件,不要触发一次就执行一次,这样做毫无节制,造成资源浪费。
应该做到相同间隔时间内执行,不要连续执行。如:根据scroll事件做的图片懒加载。
这时候可以使用函数节流来优化相关操作:
function throttle(fn, delay = 1000) {
// 节流开关
let run = true;
// 返回函数
return function () {
if (!run) {
return;
}
let timer = setTimeout(() => {
fn.apply(this, arguments);
window.clearTimeout(timer);
run = true;
}, delay);
run = false;
}
}
// 进行函数节流
let throttled = throttle(function () {
console.log('throttle');
});
// 监听resize事件
window.addEventListener('resize', throttled);
先执行 throttle
函数,返回内部函数(实际调用的函数)
改变窗口大小时,resize
事件持续触发,内部函数会根据节流开关在单位时间间隔内执行fn。
示意图:
注:在事件触发过程中,只在相同时间间隔内执行多次。
常见问题FAQ
- 免费下载或者VIP会员专享资源能否直接商用?
- 本站所有资源版权均属于原作者所有,这里所提供资源均只能用于参考学习用,请勿直接商用。若由于商用引起版权纠纷,一切责任均由使用者承担。更多说明请参考 VIP介绍。
- 提示下载完但解压或打开不了?
- 找不到素材资源介绍文章里的示例图片?
- 模板不会安装或需要功能定制以及二次开发?
发表评论
还没有评论,快来抢沙发吧!