1、防抖(debounce)
指在时间n内,函数被触发多次,但是只执行一次,执行最新的触发。也就是在时间n内,碰到新的触发,就清除之前的,重新计时。
最简单的实现
function debounce(func, wait) {
var timeout; return function () {
clearTimeout(timeout) timeout = setTimeout(func, wait); } }
修改this指向的
function debounce(func, wait) {
var timeout; return function () {
var context = this; clearTimeout(timeout) timeout = setTimeout(function(){
func.apply(context) }, wait); } }
2、节流(throttle)
当持续触发某个事件时,会有规律的每隔时间n就执行一次函数。
最简单的实现
function throttle(func, wait) {
var context, args; var previous = 0; return function() {
var now = +new Date(); context = this; args = arguments; if (now - previous > wait) {
func.apply(context, args); previous = now; } // 时间没到,啥都不干 } }
3、区别
上面的示例均为延迟防抖和延迟节流,特点在于执行时间点在周期最后。相对应的有前缘debounce和前缘throttle,这个执行时间点是立即执行的,对应上图中的1节点,之后的触发还是按照上图来,debounce的第二次执行会在停止触发之后的1s执行,throttle会在1s之后看有没有新的触发。
上文中代码来自于:
4、lodash的使用

这句话我看了半天,大概理解是这样,当有触发时,会先执行一次leading的func, 后面如果又有n次触发,就又执行一次func,n的取值可以是n >= 1
5、防抖还是节流
以一个输入框为例,来测试lodash防抖和节流的区别:

快速在输入框内输入123,函数wait时间设置为1000,并保证输入在1s内完成。
| _.debounce | leading | trailing | 结果 | 分析 |
|---|---|---|---|---|
| 1 | true | false | 打印了1 | 只有开始执行,无法获得最终输入的数据, |
| 默认 | false | true | 输入完成1s后, 打印了123 | 在输入间隔时间小于1s的情况下,打印不会执行,直到你停止输入1s后,才打印 |
| 3 | true | true | 打印1; 1s后打印123 | 开始执行一次,停止输入后1s后执行1次 |
| 4 | false | false | – | 啥都不干! |
| _.throttle | leading | trailing | 结果 | 分析 |
|---|---|---|---|---|
| 1 | true | false | 打印了1 | 同debounce |
| 2 | false | true | 1s后, 打印了123 | 从输入开始的1s后,打印1次,不同于debounce的停止输入后的1s打印 |
| 默认 | true | true | 打印1; 1s后打印123 | 开始执行一次,1s后再执行1次 |
| 4 | false | false | – | 同debounce |
总结
throttle和debounce最大的区别在于最后打印的时间不一样。
所以,选择防抖还是节流,主要取决于具体的需求。
- 输入框需求,我肯定是想要在我输入完成之后再进行请求,而不是在我输入过程中,每隔1s就发一下请求,所以我会选择防抖,并设置
wait为100或者200, 选择第2种配置。 - 对于按钮,我会设置
wait为1000,使用第1种配置。这种防抖和节流函数从结果来看没有区别。
其他场景就看你需要什么样的效果了。
6、公用组件使用防抖和节流
比如我写了一个公用组件he-input,监听@input事件,并对调用debounce处理该事件,时间间隔为1000。
// he-input.vue 组件 <el-input v-model="value" @input="inputChange"></el-input> methods: {
inputChange: _.debounce( function (v) {
console.log(v) }, 1000, {
leading: false, trailing: true, } ) }
如果一个页面只有1个he-input,那没有问题。
当一个页面有两个甚至多个he-input的时候,就会有问题。
因此,在公共组件内用防抖和节流要注意将其写在created或者mounted里面,让每一个实例都有其各自的函数。
created() {
this.inputChange = _.debounce( function (v) {
console.log(v) }, 1000, {
leading: false, trailing: true, } ) }
发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/215376.html原文链接:https://javaforall.net
