防抖:在第一次触发事件时,不立即执行函数,而是给出一个期限值比如1000ms,然后:
- 如果在1000ms内没有再次触发事件,那么就执行函数
- 如果在1000ms内再次触发事件,那么当前的计时取消,重新开始计时
规则:如果在规定时间内不断触发同一事件,只会执行一次函数。
实现:下面以滚动条事件举例,采用setTimeout这个函数来实现计时,然后借助闭包来实现:
function debounce(fn,delay){
let timer = null //借助闭包
return function() {
if(timer){
clearTimeout(timer)
}
timer = setTimeout(fn,delay)
}
}
//滚动条实现
function showTop () {
var scrollTop = document.body.scrollTop || document.documentElement.scrollTop;
console.log('滚动条位置:' + scrollTop);
}
window.onscroll = debounce(showTop,1000)
节流:就是事件触发后让函数执行一次,在设置的时间段内函数禁用,过了这段时间后才可以重新触发。
规则:如果短时间内触发同一事件,那么在函数执行一次之后,该函数在指定的时间内不再执行,直至过了这段时间才重新生效(类似于技能冷却,当技能释放之后就禁用,过几秒才可以使用)。
实现: 同样采用setTimeout来实现,加上一个变量valid来判断当前函数是否处于禁用状态:
function throttle(fn,delay){
let valid = true
return function() {
if(!valid){
//禁用状态无法触发
return false
}
// 可以触发
valid = false
setTimeout(() => {
fn()
valid = true;
}, delay)
}
}
function showTop () {
var scrollTop = document.body.scrollTop || document.documentElement.scrollTop;
console.log('滚动条位置:' + scrollTop);
}
window.onscroll = throttle(showTop,1000)