函数防抖与函数截流

函数防抖与函数截流

  1. 函数防抖
    debounce: 当持续触发事件时,一定时间段内没有再触发事件,事件处理函数才会执行一次,如果设定的时间到来之前,又一次触发了事件,就重新开始延时。
const debounce = (cb, ms) => {
    let timer = null
    return () => {
        clearTimeout(timer)
        timer = setTimeout(() => {cb}, ms)
    }
}
  1. 函数截流
    throttle: 当持续触发事件时,保证一定时间段内只调用一次事件处理函数。
const throttle = (cb, ms) => {
    let timer = true
    return () => {
        if(!timer) {
            return
        }
        timer = false
        setTimeout(() => {
            cb()
            timer = true
        })
    }
}
// 当第一次触发事件时,不会立即执行函数,而是在delay秒后才执行。而后再怎么频繁触发事件,也都是每delay时间才执行一次。当最后一次停止触发后,由于定时器的delay延迟,可能还会执行一次函数,因此可能会造成最后几次触发事件是不会被执行。
// 优化后
const throttle = (cb, ms) => {
    let timer = null
    let startTime = Date.now()
    return () => {
        let currentTime = Date.now()
        let remaining = ms - (currentTime - startTime)
        clearTimeout(timer)
        if(remaining <= 0) {
            cb()
            startTime = Date.now()
        }else {
            timer = setTimeout(() => {
                cb()
            }, remaining)
        }
    }
}
// 在节流函数内部使用开始时间startTime、当前时间curTime与delay来计算剩余时间remaining,当remaining<=0时表示该执行事件处理函数了(保证了第一次触发事件就能立即执行事件处理函数和每隔delay时间执行一次事件处理函数)。如果还没到时间的话就设定在remaining时间后再触发(保证了最后一次触发事件后还能再执行一次事件处理函数)。当然在remaining这段时间中如果又一次触发事件,那么会取消当前的计时器,并重新计算一个remaining来判断当前状态。
  1. 区别
    函数节流不管事件触发有多频繁,都会保证在规定时间内一定会执行一次真正的事件处理函数,而函数防抖只是在最后一次事件后才触发一次函数。函数防抖将几次操作合并为一此操作进行。原理是维护一个计时器,规定在delay时间后触发函数,但是在delay时间内再次触发的话,就会取消之前的计时器而重新设置。这样一来,只有最后一次操作能被触发。函数节流使得一定时间内只触发一次函数。原理是通过判断是否到达一定时间来触发函数。

猜你喜欢

转载自blog.csdn.net/HH921227/article/details/81005263