Vue的生命周期
Vue的生命周期是每个使用Vue框架的前端人员都需要掌握的知识,以此作为记录。
Vue的生命周期就是vue实例从创建到销毁的全过程,也就是new Vue() 开始就是vue生命周期的开始。Vue 实例有⼀个完整的⽣命周期,也就是从开始创建、初始化数据、编译模版、挂载Dom -> 渲染、更新 -> 渲染、卸载 等⼀系列过程,称这是Vue的⽣命周期。钩子函数是Vue生命周期中每个阶段对外开放让程序员操作Vue的接口。Vue有8个钩子函数。
借用:Vue生命周期详细图解 - 腾讯云开发者社区-腾讯云 (tencent.com)
不要慌,慢慢理解上面图的意思,一步步分析,接下来用下图加强一下理解,第一大部分是组件的创建和挂载阶段就是下图的第蓝色部分、第二个阶段就是紫色部分为:运行阶段、最后就是销毁阶段为橙色部分
组件生命周期函数的分类
四个阶段,里面存在八法方法如下表:
阶段 | 方法 | 方法 |
初始化 | beforeCreate(创建前) | created(创建后) |
挂载 | beforeMount(挂载前) | mounted(挂载后) |
更新 | beforeUpdate(更新前) | updated(更新后) |
销毁 | beforeDestroy(销毁前) | destroyed(销毁后) |
来用代码加强理解:
1、beforeCreate( 创建前 )
第一个生命周期函数
表示实例完全被创建出来之前,会执行它
此时data 和 methods 中的 数据都还没有没初始化
beforeCreate() {
//在组件还没有创建好时,是不能访问组件的任何方法和属性的
console.log('beforeCreate 组件开始创建前')
},
2、created( 创建后 )
第二个生命周期函数
data 和 methods 都已经被初始化好了
如果要调用 methods 中的方法,或者操作 data 中的数据,最早只能在 created 中操作
created() {
// 组件创建好之后可以组件实例的变量和方法
// 组件创建好之后不能访问dom
// $.post('user',function(res){
// this.username= res.data
// })
//可以在此钩子函数请求数据
console.log('created 组件创建好了')
},
3、beforeMount( 挂载前)
beforeMount 第三个生命周期函数。
表示 模板已经在内存中编辑完成了,但是尚未把 模板渲染到 页面中。
如果要调用 methods 中的方法,或者操作 data 中的数据,最早只能在 created 中操作。
执行的时候,页面中的元素,还没有被真正替换过来,只是之前写的一些模板字符串。
beforeMount() {
// 挂载组件
// 组件将要被挂载了、
// 可以访问到要挂载的目标
// 不能访问到组件的dom
// 这里可以访问到dom 但不能访问到组件的dom只能访问到要挂载的目标dom
console.log(this.$el)
console.log('beforeMount 组件开始挂载')
},
4、mounted( 挂载后)
第四个生命周期函数
表示内存中的模板已经真实的挂载到了页面中,用户已经可以看到渲染好的页面了 实例创建期间的最后一个生命周期函数,当执行完 mounted 就表示,实例已经被完全创建好了,此时,如果没有其它操作的话,这个实例,就静静的 躺在我们的内存中,一动不动
mounted() {
// 组件挂载完成
// 只有当组件挂载完成之后才能访问到组件的dom
console.log(this.$el)
console.log('mounted 组件挂载完成')
// 必须通过mounted钩子之后去获取到组件的dom元素
}
5、beforeUpdate(更新前)
界面没被更新,但是数据已更新
在数据更新之前被调用,发生在虚拟DOM重新渲染,可以在该钩子中进一步地更改状态,不会触发重复渲染过程。
beforeUpdate() {
// 只有更新和模板发生关联的数据才会触发这个钩子
// 和模板绑定的数据更新之前
console.log('beforeUpdate 和模板绑定的数据更新之前')
}
6、updated (更新后)
界面没被更新,但是数据已更新 事件执行的时候,页面和 data 数据已经保持同步了,都是最新的由于数据更改导致地虚拟DOM重新渲染会调用,调用时,组件DOM已经更新,所以可以执行依赖于DOM的操作,然后在大多是情况下,应该避免在此期间更改状态,因为这可能会导致更新无限循环,但是在服务器端渲染期间不被调用,可以用于监听某些数据的时候使用钩子
updated() {
// 只有更新和模板发生关联的数据才会触发这个钩子
// 和模板绑定的数据更新完成之后
console.log('updated 和模板绑定的数据更新完成之后')
}
7、beforeDestroy(销毁前)
在这个时候还是可以用this来获取,可以用于销毁计时器时候使用,为了防止跳转到其它页面该事件还在执行,还可以清除dom事件等
beforeDestroy() {
// 一般像页面组件 页面离开之前 保存数据 可以通过这个钩子来完成
// 当组件销毁之前触发
console.log('beforeDestroy 当组件销毁之前触发')
console.log(this.$el)
}
8、destroy(销毁后)
在实例销毁之后调用,调用后,所以的事件监听器会被移出,所有的子实例也会被销毁.
destroyed() {
// 当组件销毁之后触发
console.log('destroyed 当组件销毁之后触发')
//等待系统自动回收对象
//销毁之后组件的对象还在,但是跟vue的实例脱离了关系了
}
下面说说面试:
vue生命周期有什么作用?
它的生命周期中有多个事件钩子,让我们在控制整个Vue实例的过程时更容易形成好的逻辑关系。
第一次页面加载会触发哪几个钩子?
第一次页面加载时会触发 beforeCreate, created, beforeMount, mounted 这四个钩子函数。
DOM渲染在哪个周期中已经完成?
mounted 也就是第四个钩子函数中
created和mounted的区别?
created:在模板渲染成html前调用,即通常初始化某些属性值,然后再渲染成视图。
mounted:在模板渲染成html后调用,通常是初始化页面完成后,再对html的dom节点进行一些需要的操作。
一旦进入组件会执行那些生命周期?
前四个
beforeCreate(创建前)DOM与data都没有
created(创建后)没有DOM有data数据了
beforeMount(挂载前)没有DOM有data数据了
mounted(挂载后)有DOM也有data数据了
关于组件的传值?
父传后代(后代拿到了父的数据)
父组件使用
<Luit :str1="str1"></Luit>
子组件使用props接受数据
// 接受父传过来得数据
props:{
str1:{
type:String,
default:''
}
}
上面这种方式只能做到父传子,无法做到父传孙。
2.子组件使用父组件数据
子组件通过this.$parent.xxx来修改
3.父向孙子传值(依赖注入)provide / inject 看官方解释
父组件:
provide(){
return {
val1:'父直接向孙子传值'
}
}
子组件:
export default{
inject:['val1']
}
父修改子组件值:$refs
<Luit ref="chisd"></Luit>
methods:{
buu(){
this.$refs.chisd.str2 = '111'
}
}
子组件如何修改父组件的值?
在子组件中使用this.$parent.xxx来修改
slot/插槽
使用场景:
匿名插槽(没有名字):
具名插槽(有名字):
作用域插槽(传值):