vue中使用v-for时为什么要用到key?为什么不能用index作为key?
2020-07-15 05:11
225 查看
结论:
[code]更新DOM的时候会出现性能问题 会发生一些状态bug React 中的 key 也是如此 如果已经了解 为什么要用key,可以通过目录直接跳到下一节。
为什么要用key?
Vue 和 React 都实现了一套虚拟DOM,使我们可以不直接操作DOM元素,只操作数据便可以重新渲染页面。而隐藏在背后的原理便是其高效的Diff算法。
Vue 和 React 的虚拟DOM的Diff算法大致相同,其核心是基于两个简单的假设:
[code]两个相同的组件产生类似的DOM结构,不同的组件产生不同的DOM结构。 同一层级的一组节点,他们可以通过唯一的id进行区分。
基于以上这两点假设,使得虚拟DOM的Diff算法的复杂度从O(n^3)降到了O(n)。
用一张图简单说明一下:
当页面的数据发生变化时,Diff算法只会比较同一层级的节点:
如果节点类型不同,直接干掉前面的节点,再创建并插入新的节点。
如果节点类型相同,则会重新设置该节点的属性,从而实现节点的更新。
举个栗子:
我们希望可以在B和C之间加一个F,Diff算法默认执行起来是这样的:
即把C更新成F,D更新成C,E更新成D,最后再插入E,这样效率不高,且性能不够好。
但是,如果使用key来给每个节点做一个唯一标识,Diff算法就可以正确的识别此节点,找到正确的位置区插入新的节点。
总而言之,key的作用主要是为了高效的更新虚拟DOM 。另外vue中在使用相同标签名元素的过渡切换时,也会使用到key属性,其目的也是为了让vue可以区分它们,否则vue只会替换其内部属性而不会触发过渡效果。
这里,也建议尽可能在使用 v-for 时提供 key attribute,除非遍历输出的 DOM 内容非常简单。
为什么不能用index作为key?
举个栗子:
[code]<template> <div v-for="(item, index) in list" :key="index" >{{item.name}}</div> </template>
[code]const list = [ { id: 1, name: "Person1" }, { id: 2, name: "Person2" }, { id: 3, name: "Person3" }, { id:4, name:"Person4" } ];
此时,删除 “Person4” 是正常的,但是如果我删除 “Person2” 就会出现问题。
删除前
删除后
这个时候,除了 Person1 之外,剩下的 Person3、Person4,因为被发现与相应
key的绑定关系有变化,所以被重新渲染,这会影响性能。
如果此时
list的
item是 select 的选项,其中 Person3 是选中的,这个时候 Person2 被删除了,用 index 作为 key 就会变成是 Person4 选中的了,这就产生了bug。
如果使用唯一id作为key,删除 Person2 后,剩下的元素因为与
key的关系没有发生变化,都不会被重新渲染,从而达到提升性能的目的。此时,
list的
item作为 select 的选项,也不会出现上面所描述的bug。
相关文章推荐
- Python 为什么list不能作为字典的key?
- 在vue中,v-for的索引index在html中的使用方法
- Vue 2.0 v-for 响应式key, index及item.id参数对v-bind:key值造成差异研究
- Vue 2.0 v-for 响应式key, index及item.id参数对v-bind:key值造成差异研究
- vue使用技巧:v-for配合option时不能出现0的解决方法
- Windows程序的模块之间为什么不能使用STL容器作为参数
- vue不能在根节点中使用v-for
- Vue2.0中v-for迭代语法变化(key、index)【转】
- 浅谈VUE中演示v-for为什么要加key
- Vue使用v-for报Duplicate value found in v-for="...": "". Use track-by="$index" 错误解决方法
- vue不能在根节点中使用v-for
- 为什么不能使用成员变量的值作为成员函数的默认参数?
- vue不能在根节点中使用v-for
- vue中如何在v-for中动态的使用将index拼接字符串后绑定id属性
- 在vue中,v-for的索引index在html中的使用
- VA插件突然不能使用,弹出“the security key for....”
- GHashTable不能以字符串作为key,可以使用data list来代替
- VA插件突然不能使用,彈出“the security key for....”
- vue不能在根节点中使用v-for
- java中为什么在static中不能使用this关键字