在项目开发过程中经常遇到在input的change事件中发起请求,将用户最新输入的字符作为data传给后台,但是如果用户的输入频率过高,或者用户输入的字符还未拼成一个完整的字词,这时候发起请求会浪费网络资源,使页面卡顿。

  这时候我们就用到了函数去抖(debounce)和函数节流(throttle),首先来看一下概念:

  1,函数去抖(又称防抖)

  在事件被触发n秒后再执行回调,如果在这n秒内又被触发,则重新计时。

  未优化前代码demo:

  1. <input id="debounceTest" />
  2. <script>
  3. function ajax(value) {
  4. console.log(value+'-----------发起ajax请求')
  5. }
  6.  
  7. let inputa = document.getElementById('debounceTest')
  8.  
  9. inputa.addEventListener('keyup', function (e) {
  10. ajax(e.target.value)
  11. })
  12. </script>

  效果图:

  

  从页面中可以看到,只要触发了keyup时间,页面就会发起请求,不管用户是否输入了一个完整的字符,这样对网络资源十分浪费,在移动端甚至可能造成用户体验不流畅,系统卡顿,所以我们来对代码进行优化,如下:

优化后代码demo:

  1. function ajax(content) {
  2. console.log(content+'---------------ajax请求')
  3. }
  4.  
  5. function debounce(fun, delay) {
  6. return function (args) {
  7. let that = this
  8. let _args = args
  9. clearTimeout(fun.id)
  10. fun.id = setTimeout(function () {
  11. fun.call(that, _args)
  12. }, delay)
  13. }
  14. }
  15.  
  16. let inputb = document.getElementById('debounce')
  17.  
  18. let debounceAjax = debounce(ajax, 500)
  19.  
  20. inputb.addEventListener('keyup', function (e) {
  21. debounceAjax(e.target.value)
  22. })

  页面效果:

  

  可以看出,当用户一直在输入时,页面不会发起请求,当用户的上次输入与下次输入有一定时间间隔时,页面才会发起请求。

同样的问题还有另一种解决方法:

2,函数节流(throttle)

规定在一个单位时间内,只能触发一次函数。如果这个单位时间内触发多次函数,只有一次生效。

 还是上边的例子,这次用节流的方法实现

节流后的代码demo:

  1. function throttle(fun, delay) {
  2. let last, deferTimer
  3. return function (args) {
  4. let that = this
  5. let _args = arguments
  6. let now = +new Date()
  7. if (last && now < last + delay) {
  8. clearTimeout(deferTimer)
  9. deferTimer = setTimeout(function () {
  10. last = now
  11. fun.apply(that, _args)
  12. }, delay)
  13. }else {
  14. last = now
  15. fun.apply(that,_args)
  16. }
  17. }
  18. }
  19.  
  20. let throttleAjax = throttle(ajax, 1000)
  21.  
  22. let inputc = document.getElementById('throttle')
  23. inputc.addEventListener('keyup', function(e) {
  24. throttleAjax(e.target.value)
  25. })

页面效果:

  可以看出,不管用户的输入速度是多少,页面总是以恒定的间隔向后台发起请求。

  函数节流还可以应用于其他事件,比如mouse移动事件,页面滚动事件,resize事件等能高频次触发的事件中。

函数节流和去抖都是为了解决事件触发频率过高的问题,但是使用了不同的原理

节流是总是以固定的间隔发起请求,对高频率事件做做次数限制。去抖是固定时间段内只发送一次请求。对高频率事件做做次数限制

  以上为节流去抖的全部内部,如有错误还望指正。

JS系列1---节流,去抖(防抖)应用场景:intput请求优化,页面监听的更多相关文章

  1. 【js监听报错】页面监听js报错问题

    <html> <head> <script type="text/javascript"> // 页面监听js报错问题 onerror=hand ...

  2. JavaScript 高级系列之节流 [throttle] 与防抖 [debounce]

    一.概念 这两个东西都是为了项目优化而出现的,官方是没有具体定义的,他们的出现主要是为了解决一些短时间内连续执行的事件带来性能上的不佳和内存的消耗巨大等问题:像这类事件一般像 scroll keyup ...

  3. 前端基本知识(四):JS的异步模式:1、回调函数;2、事件监听;3、观察者模式;4、promise对象

    JavaScript语言将任务的执行模式可以分成两种:同步(Synchronous)和异步(Asychronous). “同步模式”就是一个任务完成之后,后边跟着一个任务接着执行:程序的执行顺序和排列 ...

  4. angular.js和vue.js中实现函数去抖(debounce)

    问题描述 搜索输入框中,只当用户停止输入后,才进行后续的操作,比如发起Http请求等. 学过电子电路的同学应该知道按键防抖.原理是一样的:就是说当调用动作n毫秒后,才会执行该动作,若在这n毫秒内又调用 ...

  5. JS一个非常经典的问题:在遍历数组时对DOM监听事件,索引值将始终等于遍历结束后的值

    一个简单的Tab选项卡点击事件. <style type="text/css"> ul{padding:0;margin:0;} .tab{width:400px;} ...

  6. 深入理解javascript函数进阶系列第三篇——函数节流和函数防抖

    前面的话 javascript中的函数大多数情况下都是由用户主动调用触发的,除非是函数本身的实现不合理,否则一般不会遇到跟性能相关的问题.但在一些少数情况下,函数的触发不是由用户直接控制的.在这些场景 ...

  7. 浅析 JavaScript 的函数节流和去抖

    现代网页的实现上,会有很多交互上的优化,比如常见的 滚动加载 ,输入联想 等等.他们的实现思路很简单,以滚动加载而言,无非就是去是增加一个滚动的事件监听,每次滚动判断当前的元素是否已经滚动到了用户的可 ...

  8. 【javascript】js中的函数节流和函数防抖

    一.概念解释  函数节流和函数防抖,两者都是优化高频率执行js代码的一种手段.  大家大概都知道旧款电视机的工作原理,就是一行行得扫描出色彩到屏幕上,然后组成一张张图片.由于肉眼只能分辨出一定频率的变 ...

  9. JavaScript函数节流和函数防抖之间的区别

    一.概念解释  函数节流和函数防抖,两者都是优化高频率执行js代码的一种手段.  大家大概都知道旧款电视机的工作原理,就是一行行得扫描出色彩到屏幕上,然后组成一张张图片.由于肉眼只能分辨出一定频率的变 ...

随机推荐

  1. JavaScript API for Office Outlook Add-in - “一页纸文档“

    上一篇文章 Office Add-in Model 为 Outlook Mail Add-in 提供的 JavaScript API 介绍 ,简单地在表格中列出了所有的 Object 定义,但是个人感 ...

  2. C#抓取远程Web网页信息的代码

    来自:http://www.jb51.net/article/9499.htm 通过程序自动的读取其它网站网页显示的信息,类似于爬虫程序.比方说我们有一个系统,要提取BaiDu网站上歌曲搜索排名.分析 ...

  3. Http请求的响应没有Content-Length,只有Transfer-Encoding→chunked

    如题:Http请求的响应没有Content-Length,只有Transfer-Encoding→chunked.如图 原因猜测:如果请求的响应返回是某个对象,则不会显示Content-Length, ...

  4. 学习过程中遇到的python内置函数,后续遇到会继续补充进去

    1.python内置函数isinstance(数字,数字类型),判断一个数字的数字类型(int,float,comple).是,返回True,否,返回False2.python内置函数id()可以查看 ...

  5. 移动IM开发指南2:心跳指令详解

    <移动IM开发指南>系列文章将会介绍一个IM APP的方方面面,包括技术选型.登陆优化等.此外,本文作者会结合他在网易云信多年iOS IM SDK开发的经验,深度分析实际开发中的各种常见问 ...

  6. HBase 学习之路(七)——HBase过滤器详解

    一.HBase过滤器简介 Hbase提供了种类丰富的过滤器(filter)来提高数据处理的效率,用户可以通过内置或自定义的过滤器来对数据进行过滤,所有的过滤器都在服务端生效,即谓词下推(predica ...

  7. 设计模式之策略模式和状态模式(strategy pattern & state pattern)

    本文来讲解一下两个结构比较相似的行为设计模式:策略模式和状态模式.两者单独的理解和学习都是比较直观简单的,但是实际使用的时候却并不好实践,算是易学难用的设计模式吧.这也是把两者放在一起介绍的原因,经过 ...

  8. Maven下载Jar包(bat脚本)

    1.创建一个bat文件叫download.bat 2.里面写入以下代码 call mvn -f pom.xml dependency:copy-dependencies 3.创建pom.xml文件 4 ...

  9. .Net项目中NLog的配置与使用

    引言: 因为之前在项目开发中一直都是使用的Log4Net作为项目的日志记录框架,最近忽然感觉对它已经有点腻了,所以尝试着使用了NLog作为新项目的日志记录框架(当然作为一名有志向的攻城狮永远都不能只局 ...

  10. kuangbin专题 专题一 简单搜索 非常可乐 HDU - 1495

    题目链接:https://vjudge.net/problem/HDU-1495 题意:有两个空杯(分别是N升和M升)和一罐满的可乐S升,S = N + M,三个容器可以互相倾倒,如果A倒入B,只有两 ...