防抖和节流的理解
// 参考视频: www.bilibili.com/video/BV1Vy… www.bilibili.com/video/BV1NT…
弄清防抖节流得先弄明白函数的this指向问题 (函数执行才有了this指向,this指向是由其执行方式决定 ao和go)
- 函数的独立调用:(即使在一个函数内部再写个函数,内部再独立调用,也是指向window,所以立即执行函数中的this一定指向window),实际是省去了window前缀,所以默认绑定的是window对象
- 隐式绑定:即谁调用就指向谁
- 显示绑定:call,apply,bind
- new绑定:new Foo()
对防抖和节流的理解及代码结构?
-
防抖(debounce):多次执行变成最后一次执行,即多合一(里面会有setTimeout函数,记录这个计时器的id值,根据值的有无来促发事件)
应用场景:搜索框的输入,文本框编辑器 -
节流(throttle):多次执行变成每隔一段时间执行(里面会记录点击的时间和初始时间0的差值来执行事件)
应用场景:高频事件如,快速点击,鼠标滑动,resize和scroll事件
// 防抖 -- 每次触发先清掉以前的定时器
function debounce(fn, wait) {
let timer = null;
return function () {
// 如果此时存在定时器的话,则取消之前的定时器重新记时
if (timer) {
clearTimeout(timer);
timer = null;
}
// 设置定时器,使事件间隔指定事件后执行
timer = setTimeout(() => {
fn.apply(this);
}, wait);
};
}
// 节流 - 等定时器执行完毕才开启定时器
function throttle(fn, delay) {
let timer = null
return function () {
if (!timer) {
timer = setTimeout(() => {
fn.apply(this)
timer = null
}, delay);
}
}
}
// 节流 - 用时间戳代替setTimeout的写法
function throttle(fn, delay) {
let oldTime = Date.now();
return function () {
let newTime = Date.now();
// 如果两次时间间隔超过了指定时间,则执行函数
if (newTime - oldTime >= delay) {
fn.apply(this);
oldTime = Date.now();
}
};
}