Sunny-117 / js-challenges

✨✨✨ Challenge your JavaScript programming limits step by step

Home Page:https://juejin.cn/column/7244788137410560055

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

防抖 节流

Sunny-117 opened this issue · comments

commented
function debounce(callback, time) {
    let timer = null;
    return (...args) => {
      if (timer) {
        clearTimeout(timer)
        timer = null
      }
      timer = setTimeout(() => {
        callback(...args)
      }, time);
    }
  }

function throttle(fn, delay) {
    let currentTime = Date.now()
    return (...args) => {
      nowTime = Date.now()
      if (nowTime - currentTime > delay) {
        fn(...args)
        currentTime = Date.now()
      }
    }
  }

codewhyplus版
添加了以下功能:

  • 首次立即触发
  • 取消
  • 获取返回值
function debounce(fn, delay, immediate = false, resultCallback) {
            // 1.用于记录上一次事件触发的timer 用于处理立即执行状态的inInvoke
            let timer = null
            let isInvoke = false
            // 2.触发事件时执行的函数
            const _debounce = function (...args) {
                return new Promise((resolve, reject) => {
                    try {
                        // 2.1.如果有再次触发(更多次触发)事件, 那么取消上一次的事件
                        if (timer) clearTimeout(timer)

                        let res = undefined
                        // 第一次操作是不需要延迟
                        if (immediate && !isInvoke) {
                            res = fn.apply(this, args)
                            if (resultCallback) resultCallback(res)
                            resolve(res)
                            isInvoke = true
                            return
                        }
                        // 2.2.延迟去执行对应的fn函数(传入的回调函数)
                        timer = setTimeout(() => {
                            res = fn.apply(this, args)
                            if (resultCallback) resultCallback(res)
                            resolve(res)
                            timer = null // 执行过函数之后, 将timer重新置null
                            isInvoke = false
                        }, delay);
                    } catch (error) {
                        reject(error)
                    }
                })
            }
            // 3.给_debounce绑定一个取消的函数
            _debounce.cancel = function () {
                if (timer) clearTimeout(timer)
                timer = null
                isInvoke = false
            }
            // 返回一个新的函数
            return _debounce
        }

codewhyplus版
添加了以下功能

  • 立即执行的控制
  • 尾部执行的控制
  • 鉴于尾部执行的取消
  • 获取返回值
/**
 * @param {Function} fn
 * @param {Number} interval
 * @param {Object} [{ leading = true, trailing = false }={}] 首次是否立即执行/最后一次是否执行
 * @return {*} 
 */
function throttle(fn, interval, { leading = true, trailing = false } = {}) {
    let startTime = 0
    let timer = null

    const _throttle = function (...args) {
        return new Promise((resolve, reject) => {
            try {
                // 1. 获取当前时间
                const nowTime = new Date().getTime()

                // 1.1 对立即执行进行控制
                if (!leading && startTime === 0) {
                    startTime = nowTime
                }
                // 2. 计算需要等待的时间执行函数
                const waitTime = interval - (nowTime - startTime)
                if (waitTime <= 0) {
                    // 2.1 如果此时有timer就清除 防止重复执行
                    if (timer) clearTimeout(timer)
                    const res = fn.apply(this, args)
                    resolve(res)
                    startTime = nowTime
                    timer = null
                    return
                }
                // 3. 判断是否需要执行尾部
                if (trailing && !timer) {
                    timer = setTimeout(() => {
                        const res = fn.apply(this, args)
                        resolve(res)
                        // 3.1 更新起始时间(此处不能闭包使用nowTime)
                        startTime = new Date().getTime()
                        timer = null
                    }, waitTime);
                }
            } catch (error) {
                reject(error)
            }
        })
    }
    // 4. 鉴于尾部执行的停止功能
    _throttle.cancel = function () {
        if (timer) clearTimeout(timer)
        startTime = 0
        timer = null
    }

    return _throttle
}
  const debounce = (fn, delay) =>{
          const timer = null; 
          return function(){
            clearTimeout(timer);
            setTimeout(()=>{
              fn(this, arguments);
            },delay)
          }
        }
        // 节流
        const throttle = () => {
          const timer = null;
          return function(){
            if(timer) {
              return 
            }
            timer = setTimeout(()=>{
              fn.apply(this, arguments);
              timer = null;
            },delay)
          }
        }

防抖:在一段时间内多次触发同一个事件,只执行最后一次触发的事件,而忽略之前的所有事件。

function debounce(fn, delay) {
  let timer = null;
  return function() {
    const context = this;
    const args = arguments;a
    clearTimeout(timer);
    timer = setTimeout(function() {
      fn.apply(context, args);
    }, delay);
  };
}

节流:在一段时间内多次触发同一个事件,每隔一定时间间隔执行一次事件。

function throttle(fn, delay) {
  let timer = null;
  let lastTime = 0;
  return function() {
    const context = this;
    const args = arguments;
    const nowTime = Date.now();
    if (nowTime - lastTime >= delay) {
      fn.apply(context, args);
      lastTime = nowTime;
    } else {
      clearTimeout(timer);
      timer = setTimeout(function() {
        fn.apply(context, args);
        lastTime = nowTime;
      }, delay - (nowTime - lastTime));
    }
  };
}