Vue2入门之超详细教程十三-key的作用与原理
1、简介
React、Vue中的key有什么作用?
1.虚拟DOM中key的作用:
key是虚拟DOM对象的标识,当状态中的数据发生变化时,Vue会根据[新数据]生成[新的虚拟DOM],随后Vue进行[新虚拟DOM]的差异比较,比较规则如下:
(1)旧虚拟DOM中找到了与新虚拟DOM相同的key
若虚拟DOM中内容没变,直接使用之前的真实DOM
若虚拟DOM中内容变了,则生成新的真实DOM,随后替换掉页面中之前的真实DOM
(2)旧虚拟DOM中未找到与新虚拟DOM相同的key
创建新的真实DOM,随后渲染到页面
2.用index作为key可能会引发的问题:
(1)若对数据进行:逆序添加、逆序删除等破坏顺序操作:会产生没有必要的真实DOM更新 ===》界面效果没问题,但效率低
(2)如果结构中还包含输入类DOM:会产生错误DOM更新 == >界面显示有问题
3.开发中如何选择key?
(1)最好使用每条数据的唯一表示作为key,比如id、手机号、省份证号、学号等唯一值
(2)如果不存在对数据的逆序添加、逆序删除等破坏顺序的操作,仅用于渲染列表用于展示,使用index作为key是没有问题的
学习Vue之前最后会一些HTML和CSS的基础知识,HTML基础知识 传送门,CSS基础知识 传送门。
2、key的原理
1. 问题演示
在vscode中创一个新目录,叫“12_列表渲染”,在下面创建一个“02_key的原理.html”文件,在里面输入以下代码:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>key的原理</title>
<script type="text/javascript" src="../js/development/vue.js"></script>
</head>
<body>
<!-- 准备好一个容器 -->
<div id="root">
<!-- 遍历数组 -->
<h2>人员列表(遍历数组)</h2>
<!-- click.once表示只可以点击一次 -->
<button @click.once="add">添加一个老刘</button>
<ul>
<li v-for="(p,index) of persons" :key="index">
{{p.name}}-{{p.age}}
</li>
</ul>
</div>
<script type="text/javascript">
Vue.config.productionTop=false
new Vue({
el:'#root',
data:{
persons:[
{id:'001',name:'张三',age:18},
{id:'002',name:'李四',age:19},
{id:'003',name:'王五',age:20},
]
},
methods:{
add(){
const p = {id:'004',name:'老六',age:40}
// 添加在数组最前面
this.persons.unshift(p)
}
}
})
</script>
</body>
</html>
目的在于为数组新增一条数据,@click.once表示只执行一次,this.persons.unshift()表示在数组最前面增加数据
目前看这功能实现的挺好,也没没什么问题,但是这有一个致命的问题,让我们搭配input输入框试试
<li v-for="(p,index) of persons" :key="index">
{{p.name}}-{{p.age}}
<input type="text">
</li>
来看看效果,大家可能很疑惑,这不挺好的吗,数据正常,点击新增按钮input输入框也展示正常,不着急我们在继续实验一下,首先在没有点击“添加一个老刘”按钮,时现在各个输入框输入内容,如下:
此时在点击添加按钮
这会效果就出来了,各个输入框对应的内容错位了,如果这样把数据传给后端,肯定不正确,那怎么办呢
2. 问题解决
在解决改问题之前首先说明一下产生的原因:这是因为我们用了:key="index"方式来进行数据排序,index会默认生成不同id分配给不同的数据,来验证一下:
<li v-for="(p,index) of persons" :a="index">
可以看出,index就是0、1、2这样去递增,当我们像数据头插入一条数据时,0这个下标表示的数据就是“老六”了,input输入框不会变动,其他数据依次下移,就导致了该问题,想要解决该问题,需要给数据分配唯一的id
<li v-for="(p,index) of persons" :key="p.id">
标签:key,之超,DOM,虚拟,Vue2,数据,id,name
From: https://www.cnblogs.com/lirongyang/p/17948163