手写防抖和节流函数

news2025/6/30 1:09:10

一、认识防抖debounce函数

我们用一副图来理解一下它的过程:

  • 当事件触发时,相应的函数并不会立即触发,而是会等待一定的时间;
  • 当事件密集触发时,函数的触发会被频繁的推迟;
  • 只有等待了一段时间也没有事件触发,才会真正的执行响应函数;
    在这里插入图片描述
    防抖的应用场景很多:
  • 输入框中频繁的输入内容,搜索或者提交信息;
  • 频繁的点击按钮,触发某个事件;
  • 监听浏览器滚动事件,完成某些特定操作;
  • 用户缩放浏览器的resize事件;

总结:防抖其实是延迟函数的执行,只有当等待了一段时间也没有事件触发时,才会真正去执行函数

1.2 防抖函数的案例:

在这里插入图片描述

二、手写防抖函数

我们按照如下思路来实现:

  • 防抖基本功能实现:可以实现防抖效果
    在这里插入图片描述

  • 优化一:优化参数和this指向
    在这里插入图片描述

  • 优化三:优化立即执行效果(第一次立即执行)
    在这里插入图片描述

  • 优化二:优化取消操作(增加取消功能)
    在这里插入图片描述

  • 优化四:优化返回值

在这里插入图片描述

在这里插入图片描述

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

  <input type="text">
  <button id="cancel">取消</button>

  <script src="https://cdn.jsdelivr.net/npm/underscore@1.13.1/underscore-umd-min.js"></script>
  <!-- <script src="./01_debounce-v1-基本实现.js"></script> -->
  <!-- <script src="./03_debounce-v3-立即执行.js"></script> -->
  <!-- <script src="./04_debounce-v4-取消功能.js"></script> -->
  <script src="./05_debounce-v5-函数返回值.js"></script>
  <script>
    const inputEl = document.querySelector("input")
    let counter = 0

    const inputChange = function(event) {
      console.log(`发送了第${++counter}次网络请求`, this, event)
      // 返回值
      return "aaaaaaaaaaaa"
    }

    // 防抖处理
    // inputEl.oninput = _.debounce(inputChange, 2000)
    const debounceChange = debounce(inputChange, 3000, false, (res) => {
      console.log("拿到真正执行函数的返回值:", res)
    })
    const tempCallback = (event) => {
      debounceChange(event).then(res => {
        console.log("Promise的返回值结果:", res)
      })
    }
    inputEl.oninput = tempCallback
    // 取消功能
    const cancelBtn = document.querySelector("#cancel")
    cancelBtn.onclick = function() {
      debounceChange.cancel()
    }
  </script>
</body>
</html>

在这里插入图片描述

二、认识节流throttle函数

我们用一副图来理解一下节流的过程

  • 当事件触发时,会执行这个事件的响应函数;
  • 如果这个事件会被频繁触发,那么节流函数会按照一定的频率来执行函数;
  • 不管在这个中间有多少次触发这个事件,执行函数的频繁总是固定的;
    在这里插入图片描述
    总结:节流函数是以固定的频率去触发需要执行的函数

2.2 节流的应用场景:

  • 监听页面的滚动事件;
  • 鼠标移动事件;
  • 用户频繁点击按钮操作;
  • 游戏中的一些设计;

2.3 节流函数的应用场景

在这里插入图片描述

三、手写节流函数

我们按照如下思路来实现:

  • 节流函数的基本实现:可以实现节流效果
    在这里插入图片描述

  • 优化一:控制节流第一次是否执行函数
    在这里插入图片描述

  • 优化二:控制节流最后一次是否执行函数
    在这里插入图片描述

  • 优化三:优化this参数
    在这里插入图片描述

  • 优化四:优化添加取消功能
    -

  • 优化五:优化返回值问题
    在这里插入图片描述
    在这里插入图片描述

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

  <input type="text">
  <button id="cancel">取消</button>
  
  <script src="https://cdn.jsdelivr.net/npm/underscore@1.13.1/underscore-umd-min.js"></script>
  <!-- <script src="./06_throttle-v1-基本实现.js"></script> -->
  <!-- <script src="./07_throttle-v1-leading实现.js"></script> -->
  <!-- <script src="./08_throttle-v3-traling实现.js"></script> -->
  <!-- <script src="./09_throttle-v4-this-参数.js"></script> -->
  <!-- <script src="./10_throttle-v4-取消功能.js"></script> -->
  <script src="./11_throttle-v6-函数返回值.js"></script>
  
  <script>
    const inputEl = document.querySelector("input")
    let counter = 0
    const inputChange = function(event) {
      console.log(`发送了第${++counter}次网络请求`, this, event)

      return 11111111111
    }

    // 节流处理
    // inputEl.oninput = _.throttle(inputChange, 2000)
    const _throttle = throttle(inputChange, 3000, { 
      leading: false, 
      trailing: true,
      resultCallback: function(res) {
        console.log("resultCallback:", res)
      }
     })
    const tempCallback = (...args) => {
      _throttle.apply(inputEl, args).then(res => {
        console.log("Promise:", res)
      })
    }
    inputEl.oninput = tempCallback

    // 取消功能
    const cancelBtn = document.querySelector("#cancel")
    cancelBtn.onclick = function() {
      _throttle.cancel()
    }
  </script>

</body>
</html>

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/408709.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【前端进阶】-TypeScript高级类型 | 交叉类型、索引签名类型、映射类型

前言 博主主页&#x1f449;&#x1f3fb;蜡笔雏田学代码 专栏链接&#x1f449;&#x1f3fb;【TypeScript专栏】 上篇文章讲解了TypeScript部分高级类型 详细内容请阅读如下&#xff1a;&#x1f53d; 【前端进阶】-TypeScript高级类型 | 类的初始化、构造函数、继承、成员可…

nvm安装node,配置npm 、cnpm

nvm 是什么&#xff1f; nodejs的版本管理工具&#xff0c;为了解决node.js各种版本存在不兼容现象可以通过它安装和切换不同版本的node.js 重要&#xff1a;完全卸载本地node&#xff0c; 下载链接 卸载完成之后&#xff0c;点击nvm-setup.exe安装版&#xff0c;直接运行n…

不是吧,阿sir,还有人不会制作影院订票系统前端页面吗?(拿来就用)

影院订票系统前端页面&#x1f389;案例分析&#x1f389;详细设计✨座位数据与样式定义✨座位的事件处理及相关的代码✨监听与数据格式化✨电影信息展示&#x1f389;动态操作演示图&#x1f389;源码&#xff08;附图片素材&#xff09;引言&#xff1a;大家好&#xff0c;欢…

npm和cnpm下载安装及VUE的创建

npm和cnpm下载安装及VUE的创建 1. node.js下载 node.js官网&#xff1a; http://nodejs.cn/download/ 下载安装后cmd输入以下命令查看版本 2. 配置npm 打开node.js的安装目录&#xff0c;我这里是D:\nodejs&#xff0c;在此目录下创建两个文件夹”node_global“和”node_ca…

【申请加入New Bing遇到的问题:当前无法使用此页面,cn.bing.com 重定向次数过多】

目录一.前言二.问题描述三.解决方案解决方案1:解决方案2:四.总结一.前言 前面的文章我们详细的讲解了如何加入New Bing&#xff0c;之前我们直接加入还可以直接访问&#xff0c;但是现在访问过多就会出现当前无法使用此页面&#xff0c;cn.bing.com 重定向次数过多的问题&…

eslint常见报错及解决

eslint常见报错问题1&#xff1a;Component name "index" should always be multi-word问题2&#xff1a;Newline required at end of file but not found问题3&#xff1a;Strings must use singlequote问题4&#xff1a;Expected indentation of 2 spaces but foun…

json-server|0编码实现REST API

欢迎来到我的博客 &#x1f4d4;博主是一名大学在读本科生&#xff0c;主要学习方向是前端。 &#x1f36d;目前已经更新了【Vue】、【React–从基础到实战】、【TypeScript】等等系列专栏 &#x1f6e0;目前正在学习的是&#x1f525;React框架React框架React框架&#x1f525…

uniapp中的renderjs使用

需求是用openlayers在uniapp框架下做一个移动gis类的软件&#xff0c;选择用renderjs实现地图与dom的交互&#xff0c;一开始也是小白&#xff0c;通过百度资料以及一步步测试后掌握了renderjs的使用&#xff0c;以及地图功能的实现。 一、renderjs的作用是什么&#xff1f; r…

初始vue3

如今新vue项目首选用vue3 typescript vite pinia……模式。在使用Vue2时&#xff0c;使用的是选项式api进行vue项目的开发&#xff0c;vue3在这里做了重大的更新&#xff0c;vue3使用组合式api进行对项目实例化和构建。另外需要注意vue项目需要nodeJS环境的支持&#xff0c;…

LaTex(1):使用在线表格生成器工具生成LaTex表格

目录 0 在线工具 1 常用命令&#xff1a; 1.0 编辑表格 1.1 Table—set size可以改变表格大小&#xff1a; 1.2 合并表格和拆分表格&#xff1a; 1.3 生成latex代码与复制代码&#xff1a; 2 示例 0 在线工具 表格生成器网页&#xff1a;Create LaTeX tables online –…

BootStrap基本使用

目录 BootStrap框架 BootStrap特点 bootstrap的使用 布局容器 固定宽度 完整宽度 栅格网格系统 前言 列的形式 列组合和列偏移 列排序 列嵌套 排版 标题 段落 强调 对齐效果 列表 去点列表 内联列表 定义列表 代码 表格 表单标签 文本框和文本域 单…

【web服务】nginx为什么这么受企业欢迎?看完这边文章你就懂了

&#x1f4cb; 个人简介 &#x1f496; 作者简介&#xff1a;大家好&#xff0c;我是小鹏linux&#xff0c;运维领域创作者&#xff0c;阿里云ACE认证高级工程师&#x1f61c; &#x1f4dd; 个人主页&#xff1a;小鹏linux&#x1f525; &#x1f389; 支持我&#xff1a;点赞…

【ES6丨前端进阶基础 】ES6的关键字,新特性以及解构赋值

&#x1f482; 个人主页&#xff1a;Aic山鱼 个人社区&#xff1a;山鱼社区 &#x1f4ac; 如果文章对你有所帮助请点个&#x1f44d;吧!欢迎关注、点赞、收藏(一键三连)和订阅专目录 前言 什么是ecmascrpit 一&#xff0c;let关键字的特点 1.不能重复声明变量 2.块级作用…

Http协议之Content-Type理解

Content-Type&#xff0c;翻译过来就是”内容类型“&#xff0c;在互联网中就是”互联网媒体类型“。 在互联网中&#xff0c;两台计算机经常会传输数据&#xff0c;客户端会给服务器发数据&#xff0c;服务器也会给客户端发数据。数据的类型也是有很多种的&#xff0c;我们把所…

【微信小程序系列:四】前端利用wx.setStorageSync缓存设置有效时间

先言&#xff1a; 简单来说&#xff0c;就是利用缓存&#xff0c;进行有效期的保存&#xff0c;以此前端加以判断&#xff0c;在如登录状态过期&#xff0c;操作过期等场景使用&#xff0c;扩展性还蛮多的。 官方文档 实现&#xff1a; 原理&#xff1a;就是先设置一个缓存&…

项目实战 之 vue3 + vite + pinia

目录 一、创建项目 1. 安装vite 2. 创建项目 3. 安装过程 二、项目基本配置 1. 项目icon 2. 项目标题 3. 配置 jsconfig.json 4. 设置 .prettierrc 文件 5. 生成代码片段 01 - 网址 02 - 生成 03 - 配置 04 - 使用 三、项目目录 结构划分 1. assets 2. compo…

require.context()的用法详解

require.context&#xff08;&#xff09;的用法详解&#x1f334;require.context()的介绍&#x1f33a;用法一&#xff1a;在组件内引入多个组件&#x1f33c;用法二&#xff1a;在main.js中引入大量公共组件&#x1f342;用法三&#xff1a;使用插件注册全局组件&#x1f33…

axios+vue 请求时如何携带cookie

axiosvue 请求时如何携带cookie 1&#xff0c;当符合同源策略时&#xff0c;可以直接设置 document.cookie " 你要设置的内容 " mounted() {document.cookie "ioiopipoadiasdasdbasdbas"; // 非跨域传递cookie 直接设置cookie即可this.getData(); /…

Node.js安装,npm安装yarn步骤

第一步&#xff0c;首先安装npm npm是node.js下的包管理器&#xff0c;node.js的下载网址 Node.js 1.下载安装包后一路无脑点击next最后点击finish即可&#xff0c;安装完成之后打开文件夹就是以下目录。 2.在cmd窗口输入node -v、npm -v查看版本检查是否安装成功 一般完成以…

总结JS中常用的数组的方法大全

总结JS中常用的数组方法 JS中常用的数组方法总结 数组(Array)是一种复杂的数据类型&#xff0c;它属于Object(对象)类型&#xff0c;用来将一组数组合在一起&#xff0c;通过一个变量就可以访问一组数据。在使用数组时&#xff0c;经常会搭配循环语句使用&#xff0c;从而很方便…