Open qinyuanf opened 5 years ago
当持续触发事件时,一定时间段内没有再触发事件,事件处理函数才会执行一次,如果设定时间到来之前,又触发了事件,就重新开始延时。也就是说当一个用户一直触发这个函数,且每次触发函数的间隔小于既定时间,那么防抖的情况下只会执行一次。
案例一: 搜索框的搜索联想,如果每次键盘输入都不停地向后端发送请求,用户量大且操作频繁,一般情况下后端肯定扛不住(除非公司真有钱),理想状态应该是等待用户输入操作结束或设置一个时间间隔,在该时间间隔后不再输入则发送请求。
案例二: 不断地调整浏览器的窗口大小,通过监听页面的 resize 事件进行页面适配。根据最终呈现页面的宽高进行 dom 渲染(这种情形一般是使用防抖,只需要判断最后一次的变化情况)
// 防抖 const debounce = (fn, delay) => { // 设置一个 timer let timer = null return function () { // 获取当前 return 函数作用域和参数 const args = arguments const vm = this // 清除正在执行的函数 clearTimeout(timer) timer = setTimeout(function () { fn.apply(vm, args) }, delay) } } // 如何调用 const input = document.getElementById('debounce') input.addEventListener('input', debounce((e) =>{ console.log(`向后端发送请求,参数为 ${e.target.value}`) }, 1000))
当持续触发事件时,保证在一定时间内只调用一次事件处理函数,意思是一个用户一直触发这个函数,且每次触发小于既定值,函数节流会每隔这个时间调用一次
案例一: 抢红包的按钮,其实无论点击频率有多快,发送到后端的请求数量都是有一定限制,并不是每一次点击都会到后端
案例二: 射击游戏(CF)的开枪键点击频率,并不是点击越快,打出的子弹越多,枪的射速是固定的(原谅我小时候的天真)
// 节流,时间戳 + 定时器 const throttle = (fn, delay) => { let timer = null // 开始时间 let startTime = Date.now() return function () { const endTime = Date.now() // 剩余时间 const remainTime = delay - (endTime - startTime) const vm = this const args = arguments clearTimeout(timer) if (remainTime <= 0) { fn.apply(vm, args) startTime = Date.now() } else { timer = setTimeout(fn, remainTime) } } }
// 在 vue 中使用 lodash 中的 debounce 与 throttle <template> <div @click="handleExchange">兑换</div> </template> <script> import debounce from 'lodash/debounce' export default { methods: { handleExchange: debounce(function () { // do something }, 300) } } </script>
👍
补充一个节流的小案例:滚动屏幕到底部加载更多时,不用每次 onScroll 的时候都检查到底部的距离,可以用 throttle 来周期性的检查当前位置到底部的距离。(参考 Demo)
onScroll
throttle
防抖和节流的理解和使用(by 元丰)
防抖
理解
当持续触发事件时,一定时间段内没有再触发事件,事件处理函数才会执行一次,如果设定时间到来之前,又触发了事件,就重新开始延时。也就是说当一个用户一直触发这个函数,且每次触发函数的间隔小于既定时间,那么防抖的情况下只会执行一次。
案例
案例一: 搜索框的搜索联想,如果每次键盘输入都不停地向后端发送请求,用户量大且操作频繁,一般情况下后端肯定扛不住(除非公司真有钱),理想状态应该是等待用户输入操作结束或设置一个时间间隔,在该时间间隔后不再输入则发送请求。
案例二: 不断地调整浏览器的窗口大小,通过监听页面的 resize 事件进行页面适配。根据最终呈现页面的宽高进行 dom 渲染(这种情形一般是使用防抖,只需要判断最后一次的变化情况)
原理解析
源码解析
节流
理解
当持续触发事件时,保证在一定时间内只调用一次事件处理函数,意思是一个用户一直触发这个函数,且每次触发小于既定值,函数节流会每隔这个时间调用一次
案例
案例一: 抢红包的按钮,其实无论点击频率有多快,发送到后端的请求数量都是有一定限制,并不是每一次点击都会到后端
案例二: 射击游戏(CF)的开枪键点击频率,并不是点击越快,打出的子弹越多,枪的射速是固定的(原谅我小时候的天真)
原理解析
源码解析
应用