<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          vue3 效率提升主要表現(xiàn)在哪些方面?

          共 6217字,需瀏覽 13分鐘

           ·

          2021-06-06 12:16



          前端獵手
           鏈接每一位開(kāi)發(fā)者,讓編程更有趣兒!
          關(guān)注

          vue3.0的各種表現(xiàn)還是非常棒的,相比vue2.0確實(shí)上了一個(gè)臺(tái)階,據(jù)說(shuō)在客戶(hù)端渲染效率比vue2提升了1.3~2倍,SSR渲染效率比vue2提升了2 ~3倍。在面試的過(guò)程中可能也會(huì)被問(wèn)到。

          ?? 靜態(tài)提升

          vue中有個(gè)編譯器,在vue3的package.json文件中有個(gè)@vue/compiler-sfc,vue2中叫vue-template-compiler,這兩個(gè)就是編譯器,它會(huì)把我們的模板編譯為render函數(shù),在vue3中編譯器是很智能的,在編譯的過(guò)程中,它可以發(fā)現(xiàn)哪些節(jié)點(diǎn)是靜態(tài)節(jié)點(diǎn),什么是靜態(tài)節(jié)點(diǎn)?

          靜態(tài)節(jié)點(diǎn)就是一個(gè)元素節(jié)點(diǎn),而且這個(gè)節(jié)點(diǎn)里面沒(méi)有任何動(dòng)態(tài)的內(nèi)容,就是說(shuō)沒(méi)有綁定任何動(dòng)態(tài)的屬性,這叫靜態(tài)節(jié)點(diǎn),比如:

          <template>
            <img alt="Vue logo" src="./assets/logo.png" />
            <HelloWorld msg="Hello Vue 3.0 + Vite" />
          </template>

          上述代碼中的img就是靜態(tài)節(jié)點(diǎn),它沒(méi)有綁定任何動(dòng)態(tài)的內(nèi)容

          然而vue3的編譯器會(huì)發(fā)現(xiàn)靜態(tài)節(jié)點(diǎn),然后將它進(jìn)行提升,但是在vue2中它是不在乎是靜態(tài)節(jié)點(diǎn),還是動(dòng)態(tài)節(jié)點(diǎn),一頓操作猛如虎,下面對(duì)比下:

          //vue2 的靜態(tài)節(jié)點(diǎn)
          render(){
              //創(chuàng)建一個(gè)虛擬節(jié)點(diǎn)h1,沒(méi)有任何屬性,只有內(nèi)容為"法醫(yī)",編譯后 <h1>法醫(yī)</h1>
              createVNode("h1",null,"法醫(yī)");
              //....其他代碼
          }

          //vue3 的靜態(tài)節(jié)點(diǎn)
          const hoisted = createVNode("h1",null,"法醫(yī)");
          function render(){
              //直接使用 hoisted就可以了
          }

          在vue3中,它覺(jué)得這既然是一個(gè)靜態(tài)節(jié)點(diǎn),那么肯定是不會(huì)變化的,不可能說(shuō)這一次是h1元素內(nèi)容是法醫(yī),下次變成h2元素內(nèi)容是別的了,所以說(shuō)vue3認(rèn)為既然是靜態(tài)節(jié)點(diǎn),那么就沒(méi)有必要在render函數(shù)中進(jìn)行創(chuàng)建,因?yàn)橐坏?shù)據(jù)改變,render函數(shù)會(huì)反復(fù)運(yùn)行,然后又會(huì)重新創(chuàng)建這個(gè)靜態(tài)節(jié)點(diǎn),所以為了提升效率,在vue3中,它會(huì)把靜態(tài)節(jié)點(diǎn)進(jìn)行提升,提升到render函數(shù)外面,這樣一來(lái),這個(gè)靜態(tài)節(jié)點(diǎn)永遠(yuǎn)只被創(chuàng)建一次,之后直接在render函數(shù)中使用就行了。

          示例:

          運(yùn)行一個(gè)新創(chuàng)建的vue3項(xiàng)目,在控制臺(tái)可以清楚的看到,靜態(tài)節(jié)點(diǎn)被提升到外部了。這個(gè)就是靜態(tài)節(jié)點(diǎn)的提升。

          其實(shí)不僅僅是靜態(tài)節(jié)點(diǎn)會(huì)進(jìn)行提升,而且靜態(tài)屬性也是會(huì)提升的,ok,我們來(lái)看下:

          示例:

          這是vue3新創(chuàng)建項(xiàng)目中的APP.vue組件,加一條h1元素節(jié)點(diǎn),要注意h1不是靜態(tài)節(jié)點(diǎn),它是動(dòng)態(tài)的,因?yàn)閮?nèi)容是動(dòng)態(tài)的,只有屬性是靜態(tài)的

          //APP.vue代碼
          <template>
            <h1 class="active">{{name}}</h1>
            <img alt="Vue logo" src="./assets/logo.png" />
            <HelloWorld msg="解決bug的法醫(yī)" />
          </template>

          <script>
          import HelloWorld from './
          components/HelloWorld.vue'

          export default {
            name: '
          App',
            data(){
              return{
                name:"bobo"
              }
            },
            components: {
              HelloWorld
            }
          }
          </script>

          效果如下:

          ?? 預(yù)字符串化

          這一點(diǎn)真的是特別厲害,佩服尤大大,我們可以回憶下,在平時(shí)vue開(kāi)發(fā)過(guò)程中,組件當(dāng)中沒(méi)有特別多的動(dòng)態(tài)元素,大多都是靜態(tài)元素。

          舉個(gè)栗子??:

          <div class="menu-bar-container">
              <div class="logo">
                <h1>法醫(yī)</h1>
              </div>

              <ul class="nav">
                <li><a href="">menu</a></li>
                <li><a href="">menu</a></li>
                <li><a href="">menu</a></li>
                <li><a href="">menu</a></li>
                <li><a href="">menu</a></li>
              </ul>

            </div>
            <div class="user">
              <span>{{user.name}}</
          span>
            </div>

          在這個(gè)組件中,除了span元素是動(dòng)態(tài)元素之外,其余都是靜態(tài)節(jié)點(diǎn),一般可以說(shuō)是動(dòng)靜比,動(dòng)態(tài)內(nèi)容 / 靜態(tài)內(nèi)容,比例越小,靜態(tài)內(nèi)容越多,比例越大,動(dòng)態(tài)內(nèi)容越多,vue3的編譯器它會(huì)非常智能地發(fā)現(xiàn)這一點(diǎn),當(dāng)編譯器遇到大量連續(xù)的靜態(tài)內(nèi)容,會(huì)直接將它編譯為一個(gè)普通字符串節(jié)點(diǎn),因?yàn)樗肋@些內(nèi)容永遠(yuǎn)不會(huì)變化,都是靜態(tài)節(jié)點(diǎn)。

          ?? 注意:必須是大量連續(xù)的靜態(tài)內(nèi)容才可以預(yù)字符串化哦,切記!目前是連續(xù)20個(gè)靜態(tài)節(jié)點(diǎn)才會(huì)預(yù)字符串化

          然而在vue2中,每個(gè)元素都會(huì)變成虛擬節(jié)點(diǎn),一大堆的虛擬節(jié)點(diǎn)??,這些全都是靜態(tài)節(jié)點(diǎn),在vue3中它會(huì)智能地發(fā)現(xiàn)這一點(diǎn)

          const _hoisted_1 = /*#__PURE__*/
          //createStaticVNode 靜態(tài)節(jié)點(diǎn)的意思
          _createStaticVNode("<div class=\"menu-bar-container\"><div class=\"logo\"><h1>法醫(yī)</h1></div><ul class=\"nav\"><li><a href=\"\">menu</a></li><li><a href=\"\">menu</a></li><li><a href=\"\">menu</a></li><li><a href=\"\">menu</a></li><li><a href=\"\">menu</a></li></ul></div>"1)

          瞅個(gè)簡(jiǎn)圖,感受一下vue3的魅力:

          ?? 緩存事件處理函數(shù)

          舉個(gè)栗子??:

            <button @click="count++">plus</button>

          對(duì)比處理方式:

          // vue2處理方式
          render(ctx){
              return createVNode("button",{
                  onclick:function($event){
                      ctx.count++;
                  }
              })
          }

          //vue3 處理方式
          render(ctx,_cache){
              return createVNode("button",{
                  onclick:cache[0] || (cache[0] =>($event) =>(ctx.count++))
              })
          }

          在vue2中創(chuàng)建一個(gè)虛擬節(jié)點(diǎn)button,屬性里面多了一個(gè)事件onclick,內(nèi)容就是count++

          在vue3中就有緩存了,它認(rèn)為這里的事件處理是不會(huì)變化的,不是說(shuō)這次渲染是事件函數(shù),下次就變成別的了,于是vue3會(huì)智能地發(fā)現(xiàn)這一點(diǎn),會(huì)做緩存處理,它首先會(huì)看一看緩存里面有沒(méi)有這個(gè)事件函數(shù),有的話直接返回,沒(méi)有的話就直接賦值為一個(gè)count++函數(shù),保證事件處理函數(shù)只生成一次,如下圖:

          ?? Block Tree

          Block Tree 主要為了提高新舊兩棵樹(shù)在對(duì)比差異的時(shí)候提升效率,對(duì)比差異的過(guò)程叫diff算法,也叫patch算法

          vue2在對(duì)比新舊兩棵樹(shù)的時(shí)候,并不知道哪些節(jié)點(diǎn)是靜態(tài)的,哪些節(jié)點(diǎn)是動(dòng)態(tài)的,因此只能一層一層比較,這就浪費(fèi)了大部分時(shí)間在對(duì)比靜態(tài)節(jié)點(diǎn)上。

          舉個(gè)栗子??:

          <form>
            <div>
              <label>賬號(hào):</label>
              <input v-model="user.loginId" />
            </div>

            <div>
              <label>密碼:</label>
              <input v-model="user.loginPwd" />
            </div>

          </form>

          vue2對(duì)比:

          vue2通過(guò)一系列對(duì)比之后發(fā)現(xiàn),,只有input發(fā)生了變化,也就是黃色方塊部分,藍(lán)色方塊都為靜態(tài)節(jié)點(diǎn),并沒(méi)有發(fā)生變化,這些沒(méi)有發(fā)生變化的對(duì)比都是一些沒(méi)有意義的對(duì)比,浪費(fèi)了時(shí)間,浪費(fèi)了生命

          vue3對(duì)比:

          vue3依托強(qiáng)大的編譯器,編譯器可以對(duì)每一個(gè)節(jié)點(diǎn)進(jìn)行標(biāo)記,然后在根節(jié)點(diǎn)中記錄后代節(jié)點(diǎn)中哪些是動(dòng)態(tài)節(jié)點(diǎn),記錄之后,在對(duì)比的過(guò)程中它不是整棵樹(shù)進(jìn)行對(duì)比,而是直接找到根節(jié)點(diǎn),我們叫block節(jié)點(diǎn),對(duì)比動(dòng)態(tài)節(jié)點(diǎn)數(shù)組就可以了,這樣就會(huì)略過(guò)所有的靜態(tài)節(jié)點(diǎn),也不涉及對(duì)樹(shù)的深度遍歷了,所以速度會(huì)非??欤?dāng)靜態(tài)內(nèi)容越多,效率提升就越大。

          當(dāng)然可能有小伙伴們會(huì)問(wèn),當(dāng)數(shù)據(jù)更新后可能會(huì)多出來(lái)分支,這樣處理的話會(huì)造成樹(shù)的不穩(wěn)定,樹(shù)一旦不穩(wěn)定就會(huì)出問(wèn)題了,凡是樹(shù)不穩(wěn)定的地方vue3會(huì)把它全部變成塊block,具體還是挺復(fù)雜的,我還沒(méi)研究呢,大概就是這么個(gè)意思。等我想明白了,后面再跟大家說(shuō)哈??

          ?? PatchFlag

          vue3覺(jué)得在對(duì)比每一個(gè)節(jié)點(diǎn)的時(shí)候還是在浪費(fèi)效率,盡管說(shuō)已經(jīng)跳過(guò)了所有不需要比對(duì)的節(jié)點(diǎn),但是它還要看看節(jié)點(diǎn)的元素類(lèi)型、屬性以及遞歸子節(jié)點(diǎn)有沒(méi)有變化,在針對(duì)單個(gè)節(jié)點(diǎn)對(duì)比的時(shí)候進(jìn)一步優(yōu)化,這依然需要依托vue3強(qiáng)大的編譯器,在編譯的時(shí)候,它會(huì)記錄哪個(gè)節(jié)點(diǎn)是動(dòng)態(tài)內(nèi)容,并且做上標(biāo)記

          舉個(gè)栗子??:

           <div class="active" title="法醫(yī)">
              {{user.name}}
            </div>

          vue3會(huì)在編譯的時(shí)候,它會(huì)對(duì)節(jié)點(diǎn)做上標(biāo)記,圖上標(biāo)記為1,表示在div節(jié)點(diǎn)text動(dòng)態(tài)

          舉個(gè)栗子??:

          <div :class="active" title="法醫(yī)">
              {{user.name}}
            </div>

          這個(gè)3表示在div節(jié)點(diǎn)textclass類(lèi)動(dòng)態(tài)

          ?? 好了, 以上就是我的分享,希望能對(duì)大家有所幫助,歡迎大家在評(píng)論區(qū)討論鴨~

          希望小伙伴們點(diǎn)贊 ?? 支持一下哦~ ??,我會(huì)更有動(dòng)力的 ??,晚安!

          瀏覽 35
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  欧美大香蕉四级片在线网站成熟 | 亚洲成人影音先锋 | 日本三级电影久久久影院 | 99爱视频在线观看 | AV无码中文 |