亚洲精品久久久中文字幕-亚洲精品久久片久久-亚洲精品久久青草-亚洲精品久久婷婷爱久久婷婷-亚洲精品久久午夜香蕉

您的位置:首頁技術文章
文章詳情頁

詳解vue中v-for的key唯一性

瀏覽:2日期:2022-09-29 15:15:04
目錄1. DOM Diff2. 為同一層的相同類型的元素添加 key 屬性3. key 不能是 index 下標值1. DOM Diff

要想真正了解 key 屬性的存在意義,還真得從 DOM Diff 說起,并不需要深入了解 DOM Diff 的原理,而是僅僅需要知道 DOM Diff 的工作過程即可。

Vue 和 React 都采用了運用虛擬 DOM 的方式減少瀏覽器不必要的渲染。由于 Vue 和 React 采用的都是 v = render( m ) 的方式渲染視圖的,當 model 數據發生變化時,視圖更新的方式就是重新 render DOM 元素。但是有時候我們只是改變了一個組件中的某一個 div 中的數據,如果采用原生 render 的方式去更新視圖的話,那整個組件都要更新。豈不浪費時間?

我們日常生活中碰到這樣的情況可不會全部更新,就像一個拼圖拼好了,后來其中一小塊需要更換,我們找到拿一塊直接替換就好了,絕不會說再從頭拼一次。Vue 和 React 的開發者也是這樣想的,就去想方設法優化。

我們人眼一眼就可以看出改變前和改變后的不同之處,只更新不同之處就可以了。但計算機可一眼看不出來,它必須從頭一塊快地對比,直至找到不同之處進行更新。這個將改變前和改變后進行對比找不同的過程就是 DOM Diff,DOM Diff 中的 DOM 是虛擬 DOM,也就是 JavaScript 對象,一一比較找到不同之處后,就去局部更新真正的 DOM。

在比較的過程中, 虛擬 DOM 也會構成一棵虛擬 DOM 樹,DOM Diff 的工作過程就是比較兩棵虛擬 DOM 樹上的對象節點,具體就是每一層和每一層的對應位置進行比較。正是因為計算機只會比較每一層對應位置的的兩個虛擬 DOM 元素,如果這兩棵樹中改變后的樹的某一層只是插入了一個節點,那樹的結構是不變的,DOM Diff 在比較這一層的時候就會導致錯位比較了,如下圖所示:

詳解vue中v-for的key唯一性

因為這一層的虛擬 DOM 節點對于 Vue 和 React 來說除了 DOM 節點本身外是完全沒有任何不同的,所以 DOM Diff 在比較的時候就只能按照對應位置一一比較了。

一一比較后,如果節點類型相同,那么就會復用該節點,單單局部更新該節點內不同的內容處。就像上述圖中的,如果這是 ul 下的 li 的虛擬 DOM 節點的話,那一一比較后發現節點類型相同,就復用之前的節點,將節點里面的內容進行改變,也就是,將C更新成F,D更新成C,E更新成D,最后再插入E。

上述是插入節點的情況,帶來的后果就是效率上的降低,但如果是刪除節點的情況,那帶來的后果可就不僅僅是效率了。

假如是點擊一個按鈕刪除一個 li 元素,那新舊虛擬 DOM 樹進行比較的時候,還是根據樹中每一層的對應位置一一比較,比如刪除后的 [1,2,3] 變成了 [1,3],它就會將第一個 li 和第二個 li 相比較,發現元素類型沒有變化,就會復用第一個 li,再遞歸對比 li 里面的,發現都沒變化就繼續復用。到了第二個 li 之間比較的時候,發現也都是 li 元素,那就會復用之前的li,單單將 2 變成了 3。

此時,如果復用的 li 中有子元素的話,子元素依賴的數據沒有發生變化的話,就會繼續復用之前的子組件,這樣就會導致一個錯位,如下圖:

詳解vue中v-for的key唯一性

2. 為同一層的相同類型的元素添加 key 屬性

在上述的 DOM Diff 算法中,比較的僅僅是兩棵樹同一層的對應位置,在不同層之前的元素之間是不需要比較的,而且,當 DOM Diff 的過程中發現,改變后的虛擬 DOM 和之前的虛擬 DOM 類型不同的時候,就會將之前的卸載,重新再添加改變后的元素節點。因此,上述的問題就出現在,兩棵樹中同一層的節點類型相同時,在該層添加或刪除時會降低效率或者帶來 bug。

這就是我們在 v-for 循環中生成同種類型的標簽元素時的情況,如果不為該標簽節點做點什么,就存在bug隱患,那么應該做什么呢?

答案就是為同一層的相同節點類型的節點添加一個唯一標識的 key 值,這樣,在 DOM Diff 進行配對比較時,就會將 key 相同的兩個虛擬 DOM 進行比較,而不是僅僅按照對應位置進行比較了。

這樣一來就不會導致錯位比較了,就大大提高了比較的效率,解決了 bug 隱患。

3. key 不能是 index 下標值

因為數組或對象的 index 下標值是唯一的,因此我們經常使用 index 作為 key 屬性的值,有的人說這樣是可以的,會帶來性能上的優化什么的,但使用 index 下標值是會有大大的 bug 隱患的。

這些 bug 會在你 v-for 循環的數組或對象發生添加或刪除或順序改變時。

那么為什么不能使用 index 下標呢?

其實就是因為 index 下標使用了跟沒使用了一樣,因為在添加和刪除時,某一個特定元素的 index 是會變的,比如 [1,2,3] 變成了 [1,3] 后,原來數據 3 對應的下標為2,刪除后數據 3 的下標變成了 1,這在 DOM Diff 的時候,會根據 key 值相等的進行兩兩配對比較,這數據3對應的節點前后還是對應不上,因此,使用了 index 作為 key 跟沒設置 key 是一樣的效果。

這就是為什么不要使用 index 作為 key 的原因。

因此:key 屬性值必須是獨一無二的且不會改變的

以上就是詳解vue中v-for的key唯一性的詳細內容,更多關于vue中v-for的key唯一性的資料請關注好吧啦網其它相關文章!

標簽: Vue
相關文章:
主站蜘蛛池模板: a级日本乱理伦片免费入 | 欧美高清国产在线观看 | 欧美精品一区在线看 | 欧美亚洲中日韩中文字幕在线 | 免费观看情趣v视频网站 | 精品久久久久久国产91 | 国内黄色精品 | 亚洲欧洲日韩 | 国产精品视频在 | 亚洲女同视频 | 久久国产精品一区二区 | 激情啪啪网站 | 1024国产精品 | 日韩精品中文字幕视频一区 | 国产成人精品一区二三区 | 九九爱国产 | 高清国产精品入口麻豆 | 看黄色的网址 | 成人在线一区二区三区 | 中文字幕综合网 | 免费在线黄色网址 | 国产黄色自拍视频 | 亚洲免费毛片 | 国产乱码一区二区三区四 | 免费国产人做人视频在线观看 | 麻豆国产精品入口免费观看 | 精品一区二区在线观看 1080p | 尤物视频在线观看免费 | 国产原创在线观看 | 国产午夜亚洲精品一区网站 | 九九久久久久午夜精选 | 国产成人综合网在线播放 | 日韩r级在线观看 | 大陆1区二区三区 | 一区二区三区欧美在线 | 黑人欧美一级毛片 | 鸥美肥妇特级毛片视频 | 一区二区视频免费观看 | 日本一区二区免费在线 | 亚洲黄色毛片 | 国产成人精品免费视频大全五级 |