本文记录学习vue的生命周期函数,了解vue的生命周期可以更好的找到代码出错的问题,直接放图。

image.png

从图中我们可以看到vue的组件从创建到销毁总共分为8个生命周期,分别为

  1. beforeCreate: 在实例初始化之后、进行数据侦听和事件/侦听器的配置之前同步调用。
  2. created: 在实例创建完成后被立即同步调用。在这一步中,实例已完成对选项的处理,意味着以下内容已被配置完毕:数据侦听、计算属性、方法、事件/侦听器的回调函数。
  3. beforeMount: 在挂载开始之前被调用:相关的 render 函数首次被调用。该钩子在服务器端渲染期间不被调用。
  4. mounted: 在实例挂载完成后被调用, 此时mounted不会保证所有的子组件也都被挂载完成。如果你希望等待整个视图都渲染完毕,可以在mounted内部使用this.$nextTick(()=>{})该钩子在服务器端渲染期间不被调用。
  5. beforeUpdate: 在数据发生改变后,DOM 被更新之前被调用。这里适合在现有 DOM 将要被更新之前访问它,比如移除手动添加的事件监听器。
    该钩子在服务器端渲染期间不被调用,因为只有初次渲染会在服务器端进行。
  6. updated: 在数据更改导致的虚拟 DOM 重新渲染和更新完毕之后被调用。不建议在此期间更改状态。如果要相应状态改变,通常最好使用计算属性侦听器取而代之。与mounted类似都不保证所有子组件都被更新完,需要全部更新完可以用this.$nextTick(()=>{})
  7. beforeUnmount: 在卸载组件实例之前调用。在这个阶段,实例仍然是完全正常的。该钩子在服务器端渲染期间不被调用。
  8. unmounted: 卸载组件实例后调用。调用此钩子时,组件实例的所有指令都被解除绑定,所有事件侦听器都被移除,所有子组件实例被卸载。该钩子在服务器端渲染期间不被调用。
  9. activated: 被keep-alive缓存的组件激活时调用。该钩子在服务器端渲染期间不被调用。
  10. deactivated: 被keep-alive缓存的组件失活时调用。该钩子在服务器端渲染期间不被调用。

注:所有生命周期钩子的 this 上下文将自动绑定至实例中,因此你可以访问 data、computed 和 methods。这意味着你不应该使用箭头函数来定义一个生命周期方法 (例如 created: () => this.fetchTodos())。因为箭头函数绑定了父级上下文,所以 this 不会指向预期的组件实例,并且this.fetchTodos 将会是 undefined。

下面是一个关于生命周期函数的小demo:

<!-- Lifecycle -->
<template>
  <div>
    {{num}}<button @click="updateTemplate">更新模版数据</button>
    <child-comp v-if="isShow"></child-comp>
    此子组件不会被销毁:
    <keep-alive>
      <child-comp v-if="isShow"></child-comp>
    </keep-alive>
    <button @click="isShow=!isShow">销毁子组件</button>
  </div>
</template>

<script>
import ChildComp from "@/components/ChildComp";

export default {
  name: "Lifecycle",
  components: {
    ChildComp
  },
  beforeCreate() {
    console.log('===>实例创建之前执行')
  },
  created() {
    console.log('===>创建实例后执行')
  },
  mounted() {
    // 此函数一般会被大量使用,一般在此函数中请求后端API
    console.log('===>模版编译完成后执行')
  },
  beforeMount() {
    console.log('===>模版编译完成之前执行')
  },
  beforeUpdate() {
    console.log('===>模板内容更新之前执行')
  },
  updated() {
    console.log('===>模版内容更新后执行')
  },
  beforeUnmount() {
    console.log('===>组件实例销毁之前执行')
  },
  unmounted() {
    console.log('===>组件实例销毁后执行')
  },
  activated() {
    console.log('===>激活被缓存的组件时执行')
  },
  deactivated() {
    console.log('===>被缓存的组件失活时执行')
  },
  data() {
    return {
      num: 0,
      isShow: true
    }
  },
  methods: {
    updateTemplate() {
      this.num++;
    }
  }
}
</script>
<!-- ChildComp -->
<template>
  <div>
    这个是子组件
  </div>
</template>

<script>
export default {
  name: "ChildComp",
  beforeUnmount() {
    console.log('<===子组件实例销毁之前执行')
  },
  unmounted() {
    console.log('<===子组件实例销毁后执行')
  },
  activated() {
    console.log('<===激活被缓存的子组件时执行')
  },
  deactivated() {
    console.log('<===被缓存的子组件失活时执行')
  },
}
</script>