浅析Vue组件中如何使用 防抖 和 节流

vue组件中如何使用 防抖节流?下面本篇文章通过示例带大家了解一下vue组件中使用 防抖 和 节流 控制 观察者和事件处理程序的方法,希望对大家有所帮助!

浅析Vue组件中如何使用 防抖 和 节流

在监听频繁触发的事件时,一定要多加小心,比如 用户在输入框打字、窗口大小调整、滚动、Intersection Observer 事件。

这些事件总是被频繁触发,可能 几秒一次。如果针对每次事件都发起 fetch 请求(或类似的行为),那显然是不明智的。

我们需要做的就是减缓事件处理程序的执行速度。这种缓冲技术就是 防抖(debounce) 和 节流(throttle) 。

立即学习“前端免费学习笔记(深入)”;

在本文中,你会了解到如何在 Vue 组件中 使用 防抖 和 节流 控制 观察者(watchers) 和 事件处理程序。【相关推荐:《防抖(debounce) 和 节流(throttle)》】

1. 观察者 防抖

我们先从一个简单的组件开始,我们的任务是 将用户输入到 文本框中的文本 输出到控制台:

    

{{ value }}

export default { data() { return { value: "", }; }, watch: { value(newValue, oldValue) { console.log("Value changed: ", newValue); } }};

登录后复制

打开demo:https://codesandbox.io/s/vue-input-szgn1?file=/src/App.vue

打开 demo,在 输入框 敲几个字符。每次输入时,值就会被 log 到控制台。

我们通过使用 观察者(watcher) 监听 value 数据属性 来实现了打印日志。但如果你想在 观察者的回调 中加入一个 使用 value 作为参数 的 GET 请求,那你应该不会期望太过频繁地发起请求。

我们来对 打印控制台日志 这个行为做一下 防抖。核心思想是创建一个 防抖函数,然后在 观察者 内部调用该函数。

我在这里选择了 ‘lodash.debounce’ 的 防抖实现,但你可以自由选择喜欢的实现方式。

我们来将 防抖逻辑 应用到组件:

    

{{ value }}

import debounce from "lodash.debounce";export default { data() { return { value: "", }; }, watch: { value(...args) { this.debouncedWatch(...args); }, }, created() { this.debouncedWatch = debounce((newValue, oldValue) => { console.log('New value:', newValue); }, 500); }, beforeUnmount() { this.debouncedWatch.cancel(); },};

登录后复制

试试 demo

https://codesandbox.io/s/vue-input-debounced-4vwex?file=/src/App.vue

如果你打开这个 demo,你会发现其实从用户角度来看,变化不大:你依旧可以像上一个 demo 中一样自由输入字符。

但有一个区别:只有在最后一次输入的 500ms 之后,才会将新的输入值打印日志到控制台。这说明 防抖 在生效。

观察者 的 防抖实现 只需要 3 个简单步骤:

在 create() 钩子 里,创建 防抖回调,并将其赋值到实例上:this.debouncedWatch = debounce(…, 500)。

在 观察者 回调 watch.value() { … }  中 传入正确的参数 调用 this.debouncedWatch()。

最后,beforeUnmount() 钩子中 调用 this.debouncedWatch.cancel() ,在卸载组件之前,取消所有还在 pending 的 防抖函数执行。

采用同样的方式,你可以对任意数据属性的 观察者 应用 防抖。然后就可以安全执行 防抖回调内部的一些比较重的操作,比如 网络请求、繁重的 DOM 操作,等等。

2. 事件处理器 防抖

上面一节,我展示了如何对 观察者 使用 防抖,那么常规的事件处理器呢?

我们重用之前用户输入数据到输入框的例子,但这一次会给输入框加个 事件处理器。

像往常一样,如果你没有采取任何缓冲的措施,每当值被修改时,会被打印到控制台:

  export default {  methods: {    handler(event) {      console.log('New value:', event.target.value);    }  }};

登录后复制

试试 demo:

打开这个 demo,在输入框打几个字符。看看控制台:你会发现每次你输入的时候就会有日志被打印出来。

同样,如果你会执行一些比较重的操作(比如网络请求),可就不合适了。

对 事件处理器 使用 防抖,可以参考下面这个:

  import debounce from "lodash.debounce";export default {  created() {    this.debouncedHandler = debounce(event => {      console.log('New value:', event.target.value);    }, 500);  },  beforeUnmount() {    this.debouncedHandler.cancel();  }};

登录后复制

试试 demo:

打开 demo,输入一些字符。组件只有在最后一次输入的 500ms 之后,才会将新的输入值打印日志到控制台。防抖 再一次生效了!

事件处理器 的 防抖实现 只需要 3 个步骤:

.在 create() 钩子 里,创建实例后,立刻将 防抖回调 debounce(event => {…}, 500) 赋值到 this.debouncedHandler 。

在输入框的 template 中 给 v-on:input  赋上 debouncedHandler :

最后,在卸载组件之前, 在 beforeUnmount() 钩子中 调用 this.debouncedHandler.cancel() ,取消所有还在 pending 的 函数调用。

另一方面,这些例子应用了 防抖 的技术。然而,同样的方式可以以用于创建 节流函数。

3. 注意

你可能不理解:为什么不直接在 组件的 method 选项中创建 防抖函数,然后在 template 中调用这些方法作为事件处理器?

// ...  methods: {    // Why not?    debouncedHandler: debounce(function () { ... }}, 500)  }// ...

登录后复制

这比在实例对象上创建 防抖函数 要简单的多。

例如:

  import debounce from "lodash.debounce";export default {  methods: {    // Don't do this!    debouncedHandler: debounce(function(event) {      console.log('New value:', event.target.value);    }, 500)  }};

登录后复制

试试 demo

这次不是在 created() 钩子 里创建 防抖回调了,而是将 防抖回调 赋给了 methods.debouncedHandler 。

你如果试过 demo,你会发现是有效果的!

问题是,组件使用 export default { … } 导出的 options 对象,包括方法,会被组件实例重用。

如果网页中有 2 个以上的组件实例,那么所有的组件都会应用 相同 的防抖函数 methods.debouncedHandler  — 这会导致防抖出现故障。

4. 总结

在 Vue 中,可以很轻松的对 观察者 和 事件处理器 应用 防抖 和 节流。

核心逻辑就是,在 created() 钩子 里,创建 防抖 或 节流 的回调,并赋值在实例上。

// ...  created() {    this.debouncedCallback = debounce((...args) => {      // The debounced callback    }, 500);  },// ...

登录后复制

A)然后在观察者内部调用实例上的防抖函数:

// ...  watch: {    value(...args) {      this.debouncedCallback(...args);    },  },// ...

登录后复制

B)或在 template 中设定一个事件处理器:

  

登录后复制

在这之后,每次调用 this.debouncedCallback(…args) ,就算执行频率非常高,内部的回调也能缓冲执行。

你对 Vue 中的 防抖 和 节流 还什么问题吗?欢迎提问!

更多编程相关知识,请访问:防抖(debounce) 和 节流(throttle)!!

以上就是浅析Vue组件中如何使用 防抖 和 节流的详细内容,更多请关注【创想鸟】其它相关文章!

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至253000106@qq.com举报,一经查实,本站将立刻删除。

发布者:PHP中文网,转转请注明出处:https://www.chuangxiangniao.com/p/3233080.html

(0)
上一篇 2025年4月1日 17:24:30
下一篇 2025年4月1日 17:24:42

AD推荐 黄金广告位招租... 更多推荐

相关推荐

  • vue组件是什么

    在vue中,组件是可复用的Vue实例,它拥有独一无二的组件名称,它可以扩展HTML元素,以组件名称的方式作为自定义的HTML标签。组件可大大提高了代码的复用率。 本教程操作环境:windows7系统、vue2.9.6版,DELL G3电脑。…

    2025年4月5日 编程技术
    100
  • 浅谈vue组件中怎么重新渲染?3种方式分享

    vue组件中怎么重新渲染?下面本篇文章就来给大家总结分享vue组件的重新渲染的几种方式,希望对大家有所帮助! 最近遇到一个需求,就是得把当前的组件重新渲染。这个好办,通知父组件去重新渲染就行。 下面我把我知道的vue组件的重新渲染的几种方式…

    2025年4月1日
    1400
  • 深入了解vue组件中的三个API:prop、slot和event

    不管多么复杂的组件,一定是由属性prop、事件event和插槽slot组成的。下面本篇文章就来带大家来了解一下vue组件中prop、slot和event,看看这三个api该怎么写,希望对大家有所帮助! 问题引入 是否遇到以下这种场景:开发中…

    2025年4月1日
    100
  • 一小时入门vue组件(建议收藏)

    本篇文章给大家带来了vue组件的相关知识,其中包括了怎样实例化多个vue对象、全局组件以及局部组件还有父像子传值等等,希望对大家有帮助。 初识组件应用 实例化多个vue对象 用new创建多个vue对象并命名,可以通过变量相互访问 例子:对象…

    2025年4月1日 编程技术
    100
  • 如何从0撸出一个Vue组件库并发布到npm

    如何从0撸出一个vue组件库并发布到npm?下面本篇文章手把手带大家从0开发一个vue组件库,看看怎么发布到npm,希望对大家有所帮助。 1、新建文件夹在终端打开执行 npm init -y 生成package.json如下,注意如果要发布…

    2025年4月1日
    200
  • Vue中如何使用Vue.extend扩展组件

    vue中如何使用vue.extend扩展组件 Vue是一款非常流行的JavaScript框架,主要用于构建单页应用程序。在Vue中,组件是构建用户界面的基本单元。Vue提供了很多内置组件,如按钮、输入框、下拉菜单等,但是在某些情况下,你需要…

    编程技术 2025年4月1日
    100
  • 在Vue组件中实现动态添加和删除属性

    下面我就为大家分享一篇在vue组件上动态添加和删除属性方法,具有很好的参考价值,希望对大家有所帮助。 如下所示: 在组件上添加属性 this.$set(this.data,”obj”,value’); 删…

    编程技术 2025年3月31日
    100
  • vue组件做出无限级多选菜单

    这次给大家带来vue组件做出无限级多选菜单,vue组件做出无限级多选菜单的注意事项有哪些,下面就是实战案例,一起来看一下。 wTree.vue  原理:每一个多选框都是一个节点,每个节点就是一个wTree组件,有父级(顶级level为0),…

    编程技术 2025年3月31日
    200
  • 怎样发布vue+todo-list应用

    这次给大家带来怎样发布vue+todo-list应用,发布vue+todo-list应用的注意事项有哪些,下面就是实战案例,一起来看一下。 前言 最近几个人合作完成了一个项目,发现有一些公用的基础业务组件,可以提取出来,不仅方便大家在各自模…

    2025年3月31日 编程技术
    100
  • 如何实现加载权限管理模块(详细教程)

    本篇文章给大家详细讲解了如何在权限管理模块中动态的加载vue组件的过程,有这方面需求的朋友跟着学习下吧。 本文我们主要来聊聊登录以及组件的动态加载。 登录状态保存 当用户登录成功之后,需要将当前用户的登录信息保存在本地,方便后面使用。具体实…

    编程技术 2025年3月31日
    100

发表回复

登录后才能评论