防抖和节流是啥,当一个事件高频率触发并且我们不需要这个函数执行那么多次的时候就可以用到防抖和节流。防抖和节流属性性能优化部分,毕竟资源有限,能不浪费就不浪费。
防抖
第一次触发事件时,不立刻执行函数,而是给一个延迟值,比如1s。
- 1s内如果没有再次触发该事件,那么就执行函数。
- 1s内如果再次触发该事件,那么当前的计时取消,重新开始计时
效果:如果短时间内大量触发同一事件,只会执行一次函数。简而言之,防抖就是多次操作合并为一次操作
/*
* fn [function] 需要防抖的函数
* delay [number] 毫秒,防抖期限值
*/
function debounce(fn,delay) {
let timer = null;
return function() {
if(timer) {
clearTimeout(timer) //进入该分支语句,说明当前正在一个计时过程中,并且又触发了相同事件。所以要取消当前的计时,重新开始计时
}
timer = setTimeout(fn,delay)
}
}
示例:input框输入触发事件
这里我展示的是非立即执行版的防抖,还有一种是立即执行的防抖,就是触发事件后,首先执行一下函数,然后设定一个延迟时间,这个时间内如果再次触发事件,则重新计时,这个时间内没有再次触发事件,计时完成后执行函数。
应用场景:
- 搜索输入框,用户不断输入值的时候,用防抖来节约请求资源
- 发短信、登录、提交等按钮点击太快,以至于发了多次请求,这时可以用防抖来让其只触发一次
- 鼠标的mousemove、mouseover事件
节流
让函数执行一次后,在某个时间段内暂时失效,过了这段时间后再重新激活
效果:如果短时间内大量触发同一事件,那么在函数执行一次之后,该函数在指定的时间期限内不再工作,直至过了这段时间才重新生效。简而言之就是一定时间内只触发一次函数
function throttle(fn, delay) {
let valid = true
return function () {
if (!valid) {
return false
}
// 工作时间,执行函数并且在间隔期内把状态位设为无效
valid = false
setTimeout(() => {
fn()
valid = true
}, delay)
}
}
应用场景:
- 监听浏览器滚动事件
- 鼠标的mousedown事件
- window触发resize事件的时候
lodash防抖和节流
lodash是很好用的js库,里面也集成了防抖和节流函数,下面放链接
防抖:https://www.lodashjs.com/docs/lodash.debounce
节流:https://www.lodashjs.com/docs/lodash.throttle