理解vue中组件的缓存(keep-alive)(详细总结)

简介: 理解vue中组件的缓存(keep-alive)(详细总结)

1.keep-alive是什么

keep-alive是Vue提供的一个(抽象)组件


2.作用:


主要用于保留组件状态或避免重新渲染。

3.主要内容


3.1 两个钩子函数

activated:激活,当组件在keep-alive内被切换时,进入组件触发

deactivated:缓存,当组件在keep-alive内被切换时,离开组件触发

3.2 特点

vue官方解释:

包裹动态组件时,会缓存不活动的组件实例,而不是销毁它们。

是一个抽象组件:它自身不会渲染一个 DOM 元素,也不会出现在组件的父组件链中。

3.3 注意点:

只能用在只有一个子组件的情况。如果你在其中有 v-for 则不会产生效果。

3.4 keep-alive 常用的几种方式

1. 动态组件

1. <keep-alive>
2. <component :is="view"></component>
3. </keep-alive>

2. 当出现条件判断时的子组件

1. <keep-alive>
2. <comp-a v-if="a > 1"></comp-a>
3. <comp-b v-else></comp-b>
4.

3. 结合路由使用时

1.  <keep-alive>
2. <router-view></router-view>
3.  </keep-alive>

3.5 两个属性  include 与 exclude

作用:让谁缓存,就让谁缓存

特点:

  • include - 字符串或正则表达式。只有名称匹配的组件会被缓存。
  • exclude - 字符串或正则表达式。任何名称匹配的组件都不会被缓存。

具体使用举例:

1. <keep-alive include="a,b"></keep-alive>
2. <keep-alive :include="/a|b/"></keep-alive>
3. <keep-alive :include="['a', 'b']"></keep-alive>

4.工作中的实际使用、应用


举个例子:

手机App中,点击A模块往下滑动,假设滑动到100px,接着又点击B模块,进入B页面,然后我又跳回A页面,A页面的位置依然在100px位置处。

问题来了,假设这个产品经理,非要切回A页面位置要求在每一次进入一个组件时页面的初始位置都是保持在顶部的,何解?

下面给出两个解决方法:

4.1 利用Vue中的滚动行为

前提是你是HTML5 history模式

我们在创建一个router实例的时候,可以提供一个scrollBehavior方法,该方法会在用户切换路由时触发

const router=new VueRouter({
        routes:[
            {
                path:"/",
                component:Home
            }
        ],
        scrollBehavior(to,form,savedPosition){
        //scrollBehavior方法接收to,form路由对象
        //第三个参数savedPosition当且仅当在浏览器前进后退按钮触发时才可用
        //该方法会返回滚动位置的对象信息,如果返回false,或者是一个空的对象,那么不会发生滚动
        //我们可以在该方法中设置返回值来指定页面的滚动位置,例如:
         return {x:0,y:0}
        //表示在用户切换路由时让是所有页面都返回到顶部位置
        //如果返回savedPosition,那么在点击后退按钮时就会表现的像原生浏览器一样,返回的页面会滚动过到之前按钮点击跳转的位置,大概写法如下:
         if(savedPosition){
            return savedPosition
         }else{
           return {x:0,y:0}
         }
         //如果想要模拟滚动到锚点的行为:
         if(to.hash){
           return {
             selector:to.hash
           }
         }
     }
})

4.2 利用钩子函数

在keep-alive激活会触发activated钩子函数,那么在该函数内设置scrollTop为0

5.使用的后果及消除不利影响


5.1 问题解释:

被keep-alive包裹的组件我们请求获取的数据不会再重新渲染页面,这也就出现了例如我们使用动态路由做匹配的话页面只会保持第一次请求数据的渲染结果,所以需要我们在特定的情况下强制刷新某些组件

5.2 解决一:利用include、exclude属性

思路:只缓存我们想缓存的,使用时尽量避免

解决二:利用meta属性

export default[
 {
  path:'/',
  name:'home',
  components:Home,
  meta:{
    keepAlive:true //需要被缓存的组件
 },
 {
  path:'/book',
  name:'book',
  components:Book,
  meta:{
     keepAlive:false //不需要被缓存的组件
 } 
]
<keep-alive>
  <router-view v-if="this.$route.meat.keepAlive"></router-view>
  <!--这里是会被缓存的组件-->
</keep-alive>
<keep-alive v-if="!this.$router.meta.keepAlive"></keep-alive>
<!--这里是不会被缓存的组件-->

解决三:官方提出的解决方案响应路由参数的变化

解决四:利用berforeRouteEnter实现前进刷新,后退缓存资料

解决五:利用第三方插件实现前进刷新,后退不缓存

6.vue中强制刷新组件的方法(终极解决)


6.1 v-if

思路:直接从DOM上添加和删除

总结:太简单,太粗暴(但是太省心…),性能要求高的不要用这个

6.2 使用Vue的内置forceUpdate方法(官方推荐)

使用 this.$forceUpdate();函数在需要的地方刷新

思路:通常情况下,Vue 会通过更新视图来响应依赖项中的更改。然而,当我们调用forceUpdate时,也可以强制执行更新,即使所有依赖项实际上都没有改变。

注意:这不会更新任何计算属性,调用forceUpdate仅仅强制重新渲染视图。

代码示例:

// 全局
import Vue from 'vue';
Vue.forceUpdate();
// 使用组件实例
export default {
  methods: {
    methodThatForcesUpdate() {
      // ...
      this.$forceUpdate();
      // ...
    }
  }
}

6.3 在组件上进行 key 更改(官方推荐)

思路:利用vue的虚拟DOM中diff算法,key值改变,会引起局部刷新进而达到组件刷新的目的。

实现:我们给组件来一个  : key 绑定一个变量,然后可以设置按钮点击事件让key++,从而刷新组件,也可以用watch+时间戳实现,下面贴一个示例代码

watch:{
        "key":function(){
            this.key=new Date().getTime()
        }
    }
相关文章
|
2天前
|
JavaScript
Vue使用element中table组件实现单选一行
如何在Vue中使用Element UI的table组件实现单选一行的功能。
16 5
Vue使用element中table组件实现单选一行
|
4天前
|
JavaScript
Vue2.0、Vue3.0分别使用v-model封装组件[Vue必会]
本文介绍了在Vue 2和Vue 3中如何使用`v-model`来实现组件间的双向数据绑定,包括在Vue 2中使用`value`和`input`事件,以及在Vue 3中使用`modelValue`和`update:modelValue`事件的方法。
41 22
|
1天前
|
存储 缓存 JavaScript
Vue的缓存组件 | 详解KeepAlive
Vue的缓存组件 | 详解KeepAlive
11 2
|
1天前
|
JavaScript 前端开发 Java
vue-day03 组件基础
文章介绍了Vue.js中组件的基础概念、注册格式、命名方式、全局与局部注册的区别、prop属性的详细使用以及通过prop向子组件传递数据的方法,并提供了计数器和博文小组件的实例。
|
5天前
|
存储 缓存 JavaScript
1.Vue的缓存组件 | 详解KeepAlive
1.Vue的缓存组件 | 详解KeepAlive
17 2
|
1天前
|
JavaScript API
模块化妙用!用vue3实现一个鼠标追踪器和异步加载组件
该文章展示了如何使用Vue3的Composition API实现鼠标追踪器功能,并介绍了创建异步加载组件的方法,利用TS泛型增强了组件的灵活性与可维护性。
|
1天前
|
JavaScript
vue中组件的局部注册和全局注册
本文介绍了Vue中组件的局部注册和全局注册的方法,并通过示例代码展示了如何在特定组件或整个Vue应用中注册和使用自定义组件。
|
14天前
|
canal 缓存 NoSQL
Redis缓存与数据库如何保证一致性?同步删除+延时双删+异步监听+多重保障方案
根据对一致性的要求程度,提出多种解决方案:同步删除、同步删除+可靠消息、延时双删、异步监听+可靠消息、多重保障方案
Redis缓存与数据库如何保证一致性?同步删除+延时双删+异步监听+多重保障方案
|
1月前
|
缓存 NoSQL Redis
【Azure Redis 缓存】Redission客户端连接Azure:客户端出现 Unable to send PING command over channel
【Azure Redis 缓存】Redission客户端连接Azure:客户端出现 Unable to send PING command over channel
|
30天前
|
缓存 NoSQL Java
Redis深度解析:解锁高性能缓存的终极武器,让你的应用飞起来
【8月更文挑战第29天】本文从基本概念入手,通过实战示例、原理解析和高级使用技巧,全面讲解Redis这一高性能键值对数据库。Redis基于内存存储,支持多种数据结构,如字符串、列表和哈希表等,常用于数据库、缓存及消息队列。文中详细介绍了如何在Spring Boot项目中集成Redis,并展示了其工作原理、缓存实现方法及高级特性,如事务、发布/订阅、Lua脚本和集群等,帮助读者从入门到精通Redis,大幅提升应用性能与可扩展性。
58 0