防抖和节流

什么是防抖和节流?

从本质上来说,防抖和节流是为了节省浏览器消耗,将短时间内的频繁的操作只执行一次。比如mouseMove,click,input事件,这些事件被绑定之后,可能被频繁的触发,像频繁点击按钮,鼠标滑轮一直滚动,输入框的输入事件,这些都会被不断地触发,现在就有了防抖和节流的概念,去减少操作,降低浏览器消耗。

防抖和节流的本质区别在哪?

防抖是某段时间内,如果一直触发某个事件,只会被执行一次。
节流是某段时间内如果一直触发事件,则会在规定的时间内每几秒执行一次,会不停地执行。
下面看防抖和节流的代码:

  //防抖  立即执行操作,即达到状态立即执行操作
function debounce(func,wait){
  let time
  return function(){
    let self=this   //为了保证下面箭头函数中的this指向不受影响
    if(time) clearTimeout(time)
    let flag=!time   //这里time被清除之后,还剩下一个数字字段,所以!time得到的是false
    time=setTimeout(()=>{
        time=null;
    },wait)
    if(flag) func.apply(self,arguments)
  } 
}
//后执行操作,即完成这次操作之后,等到规定时间才会执行
function debounce(func,wait){
  let self=this
  let time
  if(time) cleatTImeout(time)
  time=setTimeout(()=>{
      time=null
      func.apply(self,arguments)
  },wait)
}

从上述代码可以看到,是将内容以闭包的形式返回了,这里为了保证time的值被保存,下一次再调用函数时,相当于调用了上次闭包返回的值,相当于上次的结束时的状态。
一行一行的来看代码,先设置一个time值,为了下面能够调用,形成闭包。接着返回一个匿名函数,将这次执行完的状态返回。下一行if(time)代表如果time为true,则执行清除定时器。那么什么时候time才会为true?可以看到第一次执行时,time执行到这一行,还是空对象,之后被赋值一个定时器,所以在第一秒内的第二次之后的执行time都是true,一直执行if循环,清除定时器
那么在一直触发这个函数的时候,time定时器会一直被清除,而没有机会给time赋值为null,只有在执行了一次操作之后等待一秒,这时候time被赋值为null,再次执行函数,flag就是true,才能确保一直点击只会触发一次。

//节流 方法一:
function throttle(func,wait){
  let self=this;
  let time=0;
  return function(){
    const now=Date.now();
    if(now-time>wait){
        func.apply(this.argiments)
        time=now
    }
  }
}
方法二:
function throttle(func,wait){
   let self=this
   let time
    return function(){
      if(!time){
          time=setTimeout(()=>{
              time=null
              func.apply(this.arguments)
          },wait)
       }
    }
}

节流的思想是在一个时间段内,每隔多久执行一次。从上述代码可以看出来节流是通过设置1s后才改变这个状态,才可以继续执行下一次操作。
从代码可以看出来都是当下一次操作距离上一次操作的间隔大于设置的时间的时候,才会执行操作。

下面是完整的代码,可以看到效果:

  <!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>

</head>
<body>
    <div id="content"
        style="height:150px;line-height:150px;text-align:center; color: #fff;background-color:#ccc;font-size:80px;"></div>
    <script>
        let num = 1;
        let content = document.getElementById('content');

        function count() {
            content.innerHTML = num++;
        };
        content.onmousemove = debounce(count,1000);


        function throttle(func, wait) {
            let previous = 0;
            return function () {
                let now = Date.now();
                let args = arguments;
                if (now - previous > wait) {
                    console.log(args)
                    func.apply(this, args);
                    previous = now;
                }
            }
        }
        function throttleTimer(func,wait){
            let time
            return function(){
                let context=this
                let args=arguments;
                if(!time){
                    time=setTimeout(()=>{
                        time=null
                        func.apply(context,args)
                    },wait)
                }
            }
        }
        function debounce(func, wait) {
            let timeout;
            return function () {
                let context = this;
                let args = arguments;
                if (timeout) {
                    clearTimeout(timeout);
                    // console.log(timeout);
                 } //0
                let callNow = !timeout;  //1
                // console.log(callNow)
                timeout = setTimeout(() => {
                    timeout = null;
                }, wait)

                if (callNow) func.apply(context, args)
            }
        }
    </script>
</body>
</html>

以上是在js中的基本使用,下面看一下在vue中看一下怎么使用防抖和节流

就从最基础的输入框事件说起,我们知道有些输入框是输入的时候要发送请求的,如果一直发送请求,就会大大影响性能,所以我们要根据需要进行防抖或者节流。
先想一下防抖和节流的根本思想:
防抖:·如果一直执行,就会一直往后计算开始的时间,只有等停下操作的时候才会真正的执行操作。用代码来想就是:在规定的时间单位内,如果一直执行操作就会一直清除定时器,直至最后没有操作了,在延时之后触发事件。
节流:每隔一段时间就执行一次,原来return出去的函数是为了拿到上一步执行的time,这里可以把变量存在data中,会随着更新。在第一秒内,time第一次被赋值之后!time就一直就是false,就不会触发内部的方法,一秒之后被赋值为空之后,才能执行下一次操作。

<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0,minimal-ui:ios">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
    <script src="./vue.js"></script>
</head>
<body>
<div id="app">
    <input type="text"  @input="search" v-model="text" >
</div>

<script>
  var vm = new Vue({
    el:'#app',
    data:{
        // search:'',
        time:'',
        text:'',
        count:1,
        msg:'测试'
    },
    methods:{
        input(value){
            console.log(value)
            this.count++
            console.log('count is:' + this.count)
        },
        search() {
            //节流
            // if(!this.time){
            //     // console.log("aaa")
            //     this.time=setTimeout(()=>{
            //         this.input("ceshi")
            //         this.time=null
            //     },1000)
            // }
            //防抖
            if (this.time) {
                clearTimeout(this.time)
            }
            this.time = setTimeout(() => {
            // binding.value()
            this.input("ceshi")
                // time=null
            }, 300) 
            // 实际要进行的操作 axios.get('')之类的
            
        }
    },
 }) ;
 </script>
</body>
</html>
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 217,542评论 6 504
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,822评论 3 394
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 163,912评论 0 354
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,449评论 1 293
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,500评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,370评论 1 302
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,193评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,074评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,505评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,722评论 3 335
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,841评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,569评论 5 345
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,168评论 3 328
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,783评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,918评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,962评论 2 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,781评论 2 354

推荐阅读更多精彩内容

  • 在前端开发的过程中,我们经常会需要绑定一些持续触发的事件,如 resize、scroll、mousemove 等等...
    Grace_feb3阅读 393评论 0 0
  • 一、什么是防抖和节流?为什么用? |--引入防抖和节流解决的问题:当一个函数被频繁、无限制的被调用的时候,会加...
    stillpeng阅读 2,702评论 0 0
  • 防抖和节流在前端应用非常多,如搜索框,查询等操作,如何减少一些无效的操作,减轻服务器的压力,如一些持续发生的事件,...
    老鼠AI大米_Java全栈阅读 510评论 0 1
  • 在前端开发的过程中,我们经常会需要绑定一些持续触发的事件,如 resize、scroll、mousemove 等等...
    淘淘笙悦阅读 225,711评论 42 349
  • 18518908090微同步,曾对4K画质的价值颇多质疑,但越来越多的发行商会要求4K成片,这是大势所趋。所以剪辑...
    数字视音频解决方案阅读 4,953评论 0 0