浅谈Vue中的生命周期(vue2.x)

本文深入剖析Vue.js的生命周期,包括beforeCreate、created、beforeMount、mounted等八个关键阶段。通过示例代码展示各阶段的特点及应用场景,帮助读者更好地理解和运用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

前言


前段时间面试的时候被问到了生命周期一些问题,因为博主用生命周期只用大部分只用到了很简单的created mounted destroyed其他的用的非常少,导致答的不是太好,虽然网上一些教程已经说的非常清楚,部分还特别好,但是我还是想写一些自己的理解,能帮助大家最好,也能帮助自己复习。

vue生命周期图示


生命周期图示

官网上这张图相信大家都不陌生,官网是这么描述的:

下图展示了实例的生命周期。你不需要立马弄明白所有的东西,不过随着你的不断学习和使用,它的参考价值会越来越高。

这张图直接了当的展示了八个钩子函数依次分别是

  1. beforeCreate
  2. created
  3. beforeMount
  4. mounted
  5. beforeUpdate
  6. updated
  7. bedoreDestroy
  8. destroyed

再贴一段代码(这段代码可以复制直接使用) 参考链接

<!DOCTYPE html>
<html>
<head>
    <title></title>
    <script type="text/javascript" src="https://cdn.jsdelivr.net/vue/2.1.3/vue.js"></script>
</head>
<body>

<div id="app">
     <p id="text">{{ message }}</p>
     <button  v-on:click="fun">改变</button>
</div>

<script type="text/javascript">

  var app = new Vue({
      el: '#app',
      data: {
          message : "xuxiao is boy" 
      },
      methods:{
        fun(){
            this.message = 'hello world'
        }
      },
       beforeCreate: function () {
                console.group('beforeCreate 创建前状态===============》');
               console.log("%c%s", "color:red" , "el     : " + this.$el); //undefined
               console.log("%c%s", "color:red","data   : " + this.$data); //undefined 
               console.log("%c%s", "color:red","message: " + this.message)  
        },
        created: function () {
            console.group('created 创建完毕状态===============》');
            console.log("%c%s", "color:red","el     : " + this.$el); //undefined
               console.log("%c%s", "color:red","data   : " + this.$data); //已被初始化 
               console.log("%c%s", "color:red","message: " + this.message); //已被初始化
        },
        beforeMount: function () {
            console.group('beforeMount 挂载前状态===============》');
            console.log("%c%s", "color:red","el     : " + (this.$el)); //已被初始化
            console.log(this.$el);
               console.log("%c%s", "color:red","data   : " + this.$data); //已被初始化  
               console.log("%c%s", "color:red","message: " + this.message); //已被初始化  
        },
        mounted: function () {
            console.group('mounted 挂载结束状态===============》');
            console.log("%c%s", "color:red","el     : " + this.$el); //已被初始化
            console.log(this.$el);    
               console.log("%c%s", "color:red","data   : " + this.$data); //已被初始化
               console.log("%c%s", "color:red","message: " + this.message); //已被初始化 
        },
        beforeUpdate: function () {
            console.group('beforeUpdate 更新前状态===============》');
            console.log(document.getElementById("text").innerHTML,"````````````beforeUpdate`````````````````")
            console.log("%c%s", "color:red","el     : " + this.$el);
            console.log(this.$el);   
               console.log("%c%s", "color:red","data   : " + this.$data); 
               console.log("%c%s", "color:red","message: " + this.message); 
        },
        updated: function () {
            console.group('updated 更新完成状态===============》');
            console.log(document.getElementById("text").innerHTML,"`````````````updated```````````````")
            console.log("%c%s", "color:red","el     : " + this.$el);
            console.log(this.$el); 
               console.log("%c%s", "color:red","data   : " + this.$data); 
               console.log("%c%s", "color:red","message: " + this.message); 
        },
        beforeDestroy: function () {
            console.group('beforeDestroy 销毁前状态===============》');
            console.log("%c%s", "color:red","el     : " + this.$el);
            console.log(this.$el);    
               console.log("%c%s", "color:red","data   : " + this.$data); 
               console.log("%c%s", "color:red","message: " + this.message); 
        },
        destroyed: function () {
            console.group('destroyed 销毁完成状态===============》');
            console.log("%c%s", "color:red","el     : " + this.$el);
            console.log(this.$el);  
               console.log("%c%s", "color:red","data   : " + this.$data); 
               console.log("%c%s", "color:red","message: " + this.message)
        }
    })
</script>
</body>
</html>

下面依次讲解各个钩子函数的用处:

beforeCreate

  • 类型:Function
  • 详细:
    在实例初始化之后,数据观测 (data observer) 和 event/watcher 事件配置之前被调用。

在这个钩子函数中,数据还没有监听,没有绑定到vue对象实例,同时也没有挂载对象,更加取不到data中的数据

  • 延伸扩展:
    • 问:vue怎么在beforeCreate里获取data。(项目中基本不会遇见这类需求,但是有些面试喜欢问)
    • 答:setTimeout或者this.$nextTick
var vm = new Vue({
  el: '#app',
  data() {
    return {
      message: "hello world"
    }
  },
  beforeCreate() {
    // 相当于在初始化前告诉容器,等全执行完了再跑里面的代码。
    this.$nextTick(function () {
      console.log(this.message); // hello world
    })
  }
});

created

  • 类型:Function
  • 详细:
    在实例创建完成后被立即调用。在这一步,实例已完成以下的配置:数据观测 (data observer),属性和方法的运算,watch/event 事件回调。然而,挂载阶段还没开始,$el 属性目前不可见。

组件实例创建完成,属性已经绑定,但是DOM还未生成,$el还不存在,这一步已经可以获取data中的数据了,但是还获取不到DOM元素,还未进行挂载。

一般可以在created函数中调用ajax获取页面初始化所需的数据。

beforeMount

  • 类型:Function
  • 详细:
    在挂载开始之前被调用:相关的 render 函数首次被调用。
    该钩子在服务器端渲染期间不被调用。

完成了 el 和 data 初始化,但是还没有进行挂载~

tips:

很多新手可能不太懂挂载什么意思(博主当初就不怎么懂),博主没有找到官方的定义,但是博主在一篇react教程里,看到这句定义,给大家分享参考下:

我们把 React.js 将组件渲染,并且构造 DOM 元素然后塞入页面的过程称为组件的挂载(这个定义请好好记住)。

再用代码解释下:

<div id="app">
     <p id="text">{{ message }}</p>
</div>
...
data:{
    message : "hello world"
},
beforeMount(){
    console.log(document.getElementById("text")) // <p id="text">{{ message }}</p>
},
mounted(){
    console.log(document.getElementById("text")) // <p id="text">hello world</p>
},
...

mounted

  • 类型:Function
  • 详细:
    el 被新创建的 vm.$el 替换,并挂载到实例上去之后调用该钩子。如果 root 实例挂载了一个文档内元素,当 mounted 被调用时 vm.$el 也在文档内。

完成了 el 和 data 初始化,完成挂载~

注意 mounted 不会承诺所有的子组件也都一起被挂载。如果你希望等到整个视图都渲染完毕,可以用 vm.$nextTick 替换掉 mounted

mounted: function () {
  this.$nextTick(function () {
    // Code that will run only after the
    // entire view has been rendered
  })
}

该钩子在服务器端渲染期间不被调用。

beforeUpdate

  • 类型:Function
  • 详细:
    数据更新时调用,发生在虚拟 DOM 打补丁之前。这里适合在更新之前访问现有的 DOM,比如手动移除已添加的事件监听器。

该钩子在服务器端渲染期间不被调用,因为只有初次渲染会在服务端进行。

update

  • 类型:Function
  • 详细:
    由于数据更改导致的虚拟 DOM 重新渲染和打补丁,在这之后会调用该钩子。

当这个钩子被调用时,组件 DOM 已经更新,所以你现在可以执行依赖于 DOM 的操作。然而在大多数情况下,你应该避免在此期间更改状态。如果要相应状态改变,通常最好使用计算属性watcher 取而代之。

注意 updated 不会承诺所有的子组件也都一起被重绘。如果你希望等到整个视图都重绘完毕,可以用 vm.$nextTick 替换掉 updated

updated: function () {
  this.$nextTick(function () {
    // Code that will run only after the
    // entire view has been re-rendered
  })
}

该钩子在服务器端渲染期间不被调用。

beforeDestory

  • 类型:Function
  • 详细:
    实例销毁前调用,在这一步,实例仍然完全可用。

可以在这个钩子函数中,清除页面定义的定时器。

该钩子在服务器端渲染期间不被调用。

destroyed

  • 类型:Function
  • 详细:
    Vue 实例销毁后调用。调用后,Vue 实例指示的所有东西都会解绑定,所有的事件监听器会被移除,所有的子实例也会被销毁。

该钩子在服务器端渲染期间不被调用。

vm.$destroy(),用v-if也会触发子组件销毁,销毁一个组件的时候会触发beforeDestroy和destroyed

总结

第一次写博客,写的不好的地方多多见谅,希望能和大家共同进步。

参考链接

VUE生命周期理解

vue源码解析-生命周期

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值