函数防抖与函数节流
This commit is contained in:
parent
5470557958
commit
ab6c6e5ed5
94
source/_posts/JavaScript/函数防抖与函数节流.md
Normal file
94
source/_posts/JavaScript/函数防抖与函数节流.md
Normal file
@ -0,0 +1,94 @@
|
||||
---
|
||||
title: 函数防抖与函数节流
|
||||
date: 2019-3-12 15:28:41
|
||||
tags:
|
||||
- JavaScript
|
||||
- 函数
|
||||
categories:
|
||||
- JavaScript
|
||||
---
|
||||
|
||||
`函数防抖`与`函数节流`都是应用在该函数绑定的事件(比如keyup scroll等)可能在短时间内被频繁调用的情况
|
||||
应用后可以有效提升性能, 从而优化页面流畅度
|
||||
<!-- more -->
|
||||
|
||||
### 防抖(debounce)
|
||||
在事件被触发n秒后再执行回调函数,如果在这n秒内又被触发,则重新计时
|
||||
|
||||
比如事件在9:00被触发, 设定在10秒后执行回调函数
|
||||
之后在9:03的时候该事件再次被触发, 那么回调函数将会在9:13执行(原本会在9:10执行的回调函数不会执行)
|
||||
如果在此期间事件再次被触发, 则回调函数执行事件继续向后推移
|
||||
|
||||
#### 代码模拟实现
|
||||
```javascript
|
||||
(function(){
|
||||
function callback(content) {
|
||||
console.log('这里是需要执行的回调函数' + content)
|
||||
}
|
||||
function debounce(fun, delay) {
|
||||
return function(){
|
||||
//获取函数的作用域和形参
|
||||
let that = this
|
||||
let args = arguments
|
||||
clearTimeout(fun.id)// 清除定时器
|
||||
fun.id = setTimeout(function () {
|
||||
fun.apply(that, args)
|
||||
}, delay)
|
||||
}
|
||||
}
|
||||
// 这里设定的函数防抖时间为1s
|
||||
let debounceAjax = debounce(callback, 1000)
|
||||
document.getElementById('test-input').addEventListener('keyup', function (e) {
|
||||
debounceAjax(e.target.value)
|
||||
})
|
||||
})()
|
||||
```
|
||||
实际的效果就是在输入框当中输入内容, 当输入动作停止1秒后才会执行callback
|
||||
而不是输入一个字符就执行一次
|
||||
#### 原理
|
||||
防抖是创建一个定时器,规定在delay时间后触发函数
|
||||
但是在delay时间内再次触发的话,都会清除当前的定时器重新计时。这样一来,只有最后一次操作事件才被真正触发。
|
||||
|
||||
### 节流(throttle)
|
||||
规定一个单位时间,在这个单位时间内,只能有一次触发事件的回调函数执行,如果在同一个单位时间内某事件被触发多次,只有一次能生效。
|
||||
|
||||
比如事件在9:00被触发, 设定时间单位是10秒
|
||||
之后在9:03的时候该事件再次被触发, 那么本次触发就是无效的
|
||||
在9:00~9:10期间事件再次被触发, 均是无效的
|
||||
|
||||
#### 代码模拟实现
|
||||
```javascript
|
||||
(function(){
|
||||
function callback(content) {
|
||||
console.log('这里是需要执行的回调函数' + content)
|
||||
}
|
||||
function throttle(fn, delay) {
|
||||
let lastTime
|
||||
let timer
|
||||
delay = delay || 300 // 默认间隔为300ms
|
||||
return function() {
|
||||
let context = this
|
||||
let args = arguments
|
||||
let nowTime = +new Date()// 获取系统当前时间戳
|
||||
if (lastTime && nowTime < lastTime + delay) { // 当前距离上次执行的时间小于设置的时间间隔
|
||||
clearTimeout(timer)// 清除定时器
|
||||
timer = setTimeout(function() { // delay时间后,执行函数
|
||||
lastTime = nowTime
|
||||
fn.apply(context, args)
|
||||
}, delay)
|
||||
} else { // 当前距离上次执行的时间大于等于设置的时间,直接执行并且记录本次执行的时间戳
|
||||
lastTime = nowTime
|
||||
fn.apply(context, args)
|
||||
}
|
||||
};
|
||||
}
|
||||
let throttleAjax = throttle(callback, 1000)
|
||||
document.getElementById('test-input2').addEventListener('keyup', function (e) {
|
||||
throttleAjax(e.target.value)
|
||||
})
|
||||
})()
|
||||
```
|
||||
|
||||
### 应用场景举例
|
||||
节流: 提交按钮的防重点
|
||||
防抖: input框对输入内容的自动联想
|
||||
Loading…
x
Reference in New Issue
Block a user