vue使用防抖节流

防抖,在一定时间内,多次点击只有一次有效,节流,只要是事件不停止就不会执行。函数也很简单,两者一个不同就是一个清除定时器,一个直接返回。

先直接上代码:

function throttle(fn, time = 500){
  let timer = null;
  return function(){
    let context = this;
    let args = arguments;
    if(timer){
      clearTimeout(timer);
    }
    timer = setTimeout(() => {
      fn.apply(context, args);
      timer = null;
    }, time)
  }
}

function debounce(fn, time = 500){
  let timer = null;
  return function(){
    let context = this;
    let args = arguments;
    if(timer){
      return
    }
    timer = setTimeout(() => {
      fn.apply(context, args);
      timer = null;
    }, time)
  }
}

let vm = new Vue({
  el: '#app',
  data(){
    return {
      isVm: 'isVm'
    }
  },
  mounted(){

  },
  methods:{
    testThrottle: throttle(function(a){
      console.log('is throttle', a, this)
    }, 1000),
    testDebounce: debounce(function(a){
      console.log('is debounce', a, this);
    }, 1000),
  }
})

测试得到的效果,节流的函数,在你一直点击的情况下是不会执行,等你停止点击一秒后执行。防抖在你一直点击的情况下,每隔一秒就会执行一次。

vue方法的写法:

test(){}
test: function () {}

其实就是ES6函数的简写和正常的写法,我们防抖节流返回一个函数,所以直接调用然后通过回调执行。这边有几点要注意:

一个是防抖节流函数return的函数不能是箭头函数,否则this指向就会变成window

另一个就是使用的时候debounce(throttl)包裹的函数也不能是箭头函数,要function,否则this的指向也会指向window。

至于你用apply还是call都随意,用call就用展开符…args传参就行。

一开始我想都用箭头函数,结果this指向一直是window,箭头函数没有this,也不能用call、apply、bind。

MDN上面对this的解释:在绝大多数情况下,函数的调用方式决定了 this 的值(运行时绑定)。this 不能在执行期间被赋值,并且在每次函数被调用时 this 的值也可能会不同。箭头函数不提供自身的 this 绑定(this 的值将保持为闭合词法上下文的值)。

我的理解就是,函数的this是谁调用就指向谁,手写call、apply、bind就是用的这个原理,而箭头函数理解成声明的时候就绑定this,声明的时候就指向最外层不是箭头函数的函数,比如下面的例子:

箭头函数:

function test1(fn) {
  console.log('test1', this)//test1 {}
  fn();
}
test1.call({}, () => {
  console.log('callback', this)//callback window
})

function函数:

function test1(fn) {
  console.log('test1', this)//test1 {}
  fn();
}
test1.call({}, function () {
  console.log('callback', this)//callback window
})

无论是使用function还是箭头函数,回调函数的this都是window。

function test1(fn) {
  console.log('test1', this)//test1 {}
  fn();
}
function test2() {
  test1.call({}, () => {
    console.log('callback', this)//callback {a: 10}
  })
}
test2.apply({a: 10})

这边使用箭头函数的时候,回调函数的this就会是声明的时候的test2的this,如果我不用apply:

function test1(fn) {
  console.log('test1', this)//test1 {}
  fn();
}
function test2() {
  test1.call({}, () => {
    console.log('callback', this)//callback window
  })
}
test2()

回调函数的this指向的也是test2的this,这次是window。如果用function,test2有没有用apply,回调函数的this都是window:

function test1(fn) {
  console.log('test1', this)//test1 {}
  fn();
}
function test2() {
  test1.call({}, function(){
    console.log('callback', this)//callback window
  })
}
test2.apply({a: 10})

验证了MDN上面说的:函数的调用方式决定了 this 的值(运行时绑定),箭头函数不提供自身的 this 绑定(this 的值将保持为闭合词法上下文的值)。只不过箭头函数的this会因为闭合词法上下文的值的this的改变而改变,有点像对象的浅拷贝。

欢迎关注订阅号 coding个人笔记

  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值