1.函数防抖
-
一个频繁触发的函数,在规定的时间内重复执行函数,那么只让最后一次函数执行生效,之前的函数执行的都不生效,并且会重新触发定时器计时
-
使用的是定时器 delay=2s 第一次点击,清除上次的定时器,隔2秒时间触发定时器,那么2秒内再点一次再次清除上一次你点的2s内的定时器 接着再隔2秒时间触发定时器 .... 一直点一直循环直到最后一次才生效
-
参考:
juejin.cn/post/684490… juejin.cn/post/696871…
juejin.cn/post/703132…
4.代码
// 防抖
function dobounce(fn, delay) {
let timer = null; // 这个外层函数只会触发一次,用来存值 闭包
return function () { // 返回一个新函数
let args = arguments; // 获取参数
// 清除上一个定时器
if (timer) {
clearTimeout(timer)
}
// 开启定时器,执行延迟多少秒后执行的高频触发函数
// 为了封装的严谨性,修正this指向为调用dobounce所指的对象 并传参(若有)
timer = setTimeout(() => {
fn.apply(this, args)
}, delay)
}
}
-----------------------------------
// 测试
function task(a, b) {
console.log("我被点击了,数据是:", a, b);
}
let newTask = dobounce(task, 1000) // 返回的是一个函数体 让newTask代替task执行
// newTask(10,20,30)
let handleClick = () => {
newTask(10, 20)
}
2.函数节流
一个频繁触发的函数,在规定在一个单位时间内,只能触发一次函数,之后的函数执行都不生效如果这个单位时间内触发多次函数,只有第一次函数执行有效
// 节流
function throttle(fn, delay) {
let start = 0 // 定义初始时间 这个外层函数只会触发一次,用来存值 闭包
return function () {
let args = arguments
let now = Date.now() // 返回自 1970 年 1 月 1 日 00:00:00 (UTC) 到当前时间的毫秒数
// console.log(now,start,now - start,delay);
if(now - start > delay){ // 当前时间 - 开始时间 大于 延迟时间 那么就执行函数
start = now // 将上次的时间改为当前时间
fn.apply(this,args) // 执行函数
}
}
}
---------------------------------
// 测试
function task1(a, b) {
console.log("我被点击了,数据是:", a, b);
}
let newTask1 = throttle(task1, 2000) // 返回的是一个函数体
// newTask1(10,20,30)
let handleClick1 = () => {
newTask1(10, 20, 30)
}
3.总结:
- 函数防抖和函数节流都是防止某一时间频繁触发,但是这两兄弟之间的原理却不一样。
- 函数防抖是某一段时间内只执行一次,而函数节流是间隔时间执行。
3.1 结合应用场景
debounce:
- search搜索联想,用户在不断输入值时,用防抖来节约请求资源。
- window触发resize的时候,不断的调整浏览器窗口大小会不断的触发这个事件,用防抖来让其只触发一次
throttle:
- 鼠标不断点击触发,mousedown(单位时间内只触发一次)
- 监听滚动事件,比如是否滑到底部自动加载更多,用throttle来判断