從源碼入手,探究vue中key的做用和工做原理

前言

提及vue中的key,只要使用vue那確定是都使用過。要說做用嘛,你們大概都瞭解,不就是組件或者元素的複用和渲染嗎?但是其中的原理又是什麼呢?下面咱們來深刻源碼一探究竟,let‘go!vue

key值的做用

key值大多狀況下使用在循環語句中,從本質來說主要做用大概有如下兩點:node

  1. 主要用在 Vue 的虛擬 DOM 算法,在新舊 nodes 對比時辨識 VNodes,至關於惟一標識ID。
  2. Vue 會盡量高效地渲染元素,一般會複用已有元素而不是從頭開始渲染, 所以使用key值能夠提升渲染效率,同理,改變某一元素的key值會使該元素從新被渲染。

工做原理

那麼key值的工做原理是怎麼樣的呢?直接上源碼算法

// 由於key值主要使用在虛擬DOM算法,即diff算法中。因此咱們在src\core\vdom\patch.js文件中,從源碼級別進行探討

// 先說這裏的核心方法patch。這個方法在vue進行update,即將render函數(虛擬DOM生成的函數)轉化爲真實DOM的時候執行,裏面主要首次渲染建立真實DOM樹,進行虛擬DOM節點直接的對比,以及真實DOM的更新的一系列操做,而且會進行一系列判斷和兼容處理,其中就有對key值的具體使用

// 這個方法主要在patch方法中調用
// 方法名很語義化 sameVnode === 相同虛擬DOM節點
function sameVnode (a, b) {
    return (
        // 判斷a, b兩個Vnode上的key值是否相等
        a.key === b.key && (
            (
                a.tag === b.tag &&
                a.isComment === b.isComment &&
                isDef(a.data) === isDef(b.data) &&
                sameInputType(a, b)
            ) || (
                isTrue(a.isAsyncPlaceholder) &&
                a.asyncFactory === b.asyncFactory &&
                isUndef(b.asyncFactory.error)
            )
        )
    )
}


// 在簡單說下patchVnode方法的做用,這個方法會在patch方法裏面調用,是直接對比新舊虛擬Vnode節點,也是diff算法真正執行的地方

// 如下代碼在patchVnode方法中
// 在開始進行判斷,符合條件的話就跳出方法,再也不進行下面的diff對比
// vnode.key === oldVnode.key判斷雙方是否是同一個組件
if (isTrue(vnode.isStatic) &&
    isTrue(oldVnode.isStatic) &&
    vnode.key === oldVnode.key &&
    (isTrue(vnode.isCloned) || isTrue(vnode.isOnce))
    ) {
        vnode.componentInstance = oldVnode.componentInstance
        return
}

結論

在例子中能夠看出,對Vnode進行patch的時候會調用sameVnode方法,裏面會使用key值是否相等來判斷Vnode是否爲同一個。而且在對比過程當中做爲組件複用的一個判斷條件。
因此key值是在DOM樹進行diff算法時候發揮做用。一個是用來判斷新舊Vnode是否爲同一個,從而進行下一步的比較以及渲染。另一個做用就是判斷組件是否能夠複用,是否須要從新渲染。dom

相關文章
相關標籤/搜索