1. 程式人生 > 其它 >VUE學習九,生命週期

VUE學習九,生命週期

Vue例項有一個完整的生命週期,也就是從開始建立、初始化資料、編譯模板、掛載Dom、渲染→更新→渲染、銷燬等一系列過程,我們稱這是Vue的生命週期。通俗說就是Vue例項從建立到銷燬的過程,就是生命週期。

一、每一個元件或者例項都會經歷一個完整的生命週期,總共分為三個階段:初始化、執行中、銷燬

  1. 例項、元件通過new Vue() 創建出來之後會初始化事件和生命週期,然後就會執行beforeCreate鉤子函式,這個時候,資料還沒有掛載呢,只是一個空殼,無法訪問到資料和真實的dom,一般不做操作

  2. 掛載資料,繫結事件等等,然後執行created函式,這個時候已經可以使用到資料,也可以更改資料,在這裡更改資料不會觸發updated函式,在這裡可以在渲染前倒數第二次更改資料的機會,不會觸發其他的鉤子函式,一般可以在這裡做初始資料的獲取

  3. 接下來開始找例項或者元件對應的模板,編譯模板為虛擬dom放入到render函式中準備渲染,然後執行beforeMount鉤子函式,在這個函式中虛擬dom已經建立完成,馬上就要渲染,在這裡也可以更改資料,不會觸發updated,在這裡可以在渲染前最後一次更改資料的機會,不會觸發其他的鉤子函式,一般可以在這裡做初始資料的獲取

  4. 接下來開始render,渲染出真實dom,然後執行mounted鉤子函式,此時,元件已經出現在頁面中,資料、真實dom都已經處理好了,事件都已經掛載好了,可以在這裡操作真實dom等事情...

  5. 當元件或例項的資料更改之後,會立即執行beforeUpdate,然後vue的虛擬dom機制會重新構建虛擬dom與上一次的虛擬dom樹利用diff演算法進行對比之後重新渲染,一般不做什麼事兒

  6. 當更新完成後,執行updated,資料已經更改完成,dom也重新render完成,可以操作更新後的虛擬dom

  7. 當經過某種途徑呼叫$destroy方法後,立即執行beforeDestroy,一般在這裡做一些善後工作,例如清除計時器、清除非指令繫結的事件等等

  8. 元件的資料繫結、監聽...去掉後只剩下dom空殼,這個時候,執行destroyed,在這裡做善後工作也可以

二、示範程式碼

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta 
name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>VUE生命週期學習</title> </head> <body> <div id="app-9"> <comp1></comp1> </div> <template id="temp1"> <div> <p class="myp">A元件</p> <button @click="destroy">destroy</button> <br/> <input type="text" v-model="msg"> <p>msg:{{msg}}</p> </div> </template> </body> <script src="../js/vue.js"></script> <script> //生命週期:初始化階段 執行階段 銷燬階段 Vue.component("comp1",{ template:"#temp1", data:function(){ return {msg:'hello'} }, timer:null, methods:{ destroy:function(){ this.$destroy()// } }, beforeCreate:function(){ console.log('beforeCreate:剛剛new Vue()之後,這個時候,資料還沒有掛載呢,只是一個空殼') console.log(this.msg)//undefined console.log(document.getElementsByClassName("myp")[0])//undefined }, created:function(){ console.log('created:這個時候已經可以使用到資料,也可以更改資料,在這裡更改資料不會觸發updated函式') this.msg+='!!!' console.log('在這裡可以在渲染前倒數第二次更改資料的機會,不會觸發其他的鉤子函式,一般可以在這裡做初始資料的獲取') console.log('接下來開始找例項或者元件對應的模板,編譯模板為虛擬dom放入到render函式中準備渲染') }, beforeMount:function(){ console.log('beforeMount:虛擬dom已經建立完成,馬上就要渲染,在這裡也可以更改資料,不會觸發updated') this.msg+='@@@@' console.log('在這裡可以在渲染前最後一次更改資料的機會,不會觸發其他的鉤子函式,一般可以在這裡做初始資料的獲取') console.log(document.getElementsByClassName("myp")[0])//undefined console.log('接下來開始render,渲染出真實dom') }, // render:function(createElement){ // console.log('render') // return createElement('div','hahaha') // }, mounted:function(){ console.log('mounted:此時,元件已經出現在頁面中,資料、真實dom都已經處理好了,事件都已經掛載好了') console.log(document.getElementsByClassName("myp")[0]) console.log('可以在這裡操作真實dom等事情...') // this.$options.timer = setInterval(function () { // console.log('setInterval') // this.msg+='!' // }.bind(this),500) }, beforeUpdate:function(){ //這裡不能更改資料,否則會陷入死迴圈 console.log('beforeUpdate:重新渲染之前觸發') console.log('然後vue的虛擬dom機制會重新構建虛擬dom與上一次的虛擬dom樹利用diff演算法進行對比之後重新渲染') }, updated:function(){ //這裡不能更改資料,否則會陷入死迴圈 console.log('updated:資料已經更改完成,dom也重新render完成') }, beforeDestroy:function(){ console.log('beforeDestory:銷燬前執行($destroy方法被呼叫的時候就會執行),一般在這裡善後:清除計時器、清除非指令繫結的事件等等...') // clearInterval(this.$options.timer) }, destroyed:function(){ console.log('destroyed:元件的資料繫結、監聽...都去掉了,只剩下dom空殼,這裡也可以善後') } }) new Vue({ }).$mount('#app-9') </script> </html>

三、輸出結果如下圖

四、官方生命週期圖

本文參考:

https://www.cnblogs.com/happ0/p/8075562.html