在前端开发中有一部分用户行为会频繁出发事件执行。而对于DOM操作、资源加载等耗性能的处理,很可能导致界面卡顿,甚至浏览器崩溃。函数节流(throttle)和函数的防抖(debounce)就是为了解决类似需求应运而生
秒懂它们的概念
函数防抖(debounce)和函数节流(throttle)都是为了缓解函数频繁调用,它们相似,但有区别
如上图,一条竖线代表一次函数调用,函数防抖是间隔超过一定时间后才会执行,函数节流是一定时间段内只执行一次
节流(throttle)
函数节流就是预定一个函数只有大于等于执行周期时才执行,周期内调用不执行。好像水滴攒到一定重量才会落下一样。
通俗来讲节流,就是指连续触发事件但是在 n 秒中只执行一次函数。节流会稀释函数的执行频率
- 窗口调整(size)
- 页面滚动(scroll)
- 抢购疯狂点击(mousedown)
时间戳版实现:
function throttle(func, delay) {
let last = 0
return function () {
let now = +new Date()
if (now - last > delay) {
func.apply(this, arguments)
last = now
}
}
}
定时器版实现:
function throttle(func, wait) {
var timeout
return function (){
var _this = this
var args = arguments
if (!timeout) {
timeout = setTimeout(function (){
timeout = null
func.apply(_this, args)
}, wait)
}
}
}
我们应该可以很容易的发现,其实时间戳版和定时器版的节流函数的区别就是,时间戳版的函数触发是在时间段内开始的时候,而定时器版的函数触发是在时间段内结束的时候
防抖(debounce)
防抖函数就是在函数需要频繁触发情况下,只有足够空闲的时间,才执行一次。好像公家车司机会等人都上车后才出站。
通俗来讲防抖,就是指触发事件后在 n 秒内函数只能执行一次,如果在 n 秒内又触发了事件,则会重新计算函数执行时间
- 实时搜索(keyup)
- 拖拽(mousemove)
function debounce(func, delay){
var timer = null
return function (){
var _this = this, args = arguments
clearTimeout(timer)
timer = setTimeout(function (){
func.apply(_this, args)
}, dealy)
}
}