目录
1. 数组翻转 2. 数组截取 3. 更新值
- 数组变更方法,就会导致v-for更新,页面更新
(push,pop,shift,unshift,splice,sort,reverse)
- 数组非变更方法,返回新数组,不会导致v-for更新,可采用覆盖数组 或 this.$set
(filter,concat,slice)
<body>
<div id="app">
<ul>
<li v-for="(val,index) in arr">{{val}}</li>
</ul>
<button @click="revBtn">数组反转</button>
<button @click="sliceFn">截取前3个</button>
<button @click="updateFn">更新第一个元素值</button>
</div>
</body>
<script>
var vm = new Vue({
el: '#app',
data: {
arr: [1, 2, 3, 4, 5, 6, 7, 8, 9],
},
methods: {
// 数组反转,可以让v-for更新
revBtn() {
this.arr.reverse()
// console.log(this.arr)
},
sliceFn() {
// 数组slice 不会造成v-for更新
// slice不会改变原数组
this.arr.slice(0, 3)
// console.log(this.arr)
// 解决v-for更新,覆盖原始数组
let newArr = this.arr.slice(0, 3)
this.arr = newArr
},
updateFn() {
// 更新某个值的时候,v-for时监测不到的
this.arr[0] = 1999
// 解决v-for更新,this.$set
// 参数1 更新目标结构(对象/数组)
// 参数2 更新位置
// 参数3 更新值
this.$set(this.arr, 0, 1999)
}
}
})
</script>
v-for如何更新DOM
v-for尝试复用标签,就地更新内容
<body>
<div id="app">
<!--
问题:JS原生数组变化,如何更新页面
重新渲染 整个DOM结构都要重新渲染
重新渲染, 就引起页面的重绘和回流(页面结构或样式发生变化) 性能不好
-->
<ul>
<li v-for="(item,index) in arr">{{item}}</li>
</ul>
<button @click="fn">下标1的位置插入新的元素</button>
</div>
</body>
<script>
var vm = new Vue({
el: '#app',
data: {
arr: ['aaa', 'bbb', 'ccc'],
},
methods: {
fn() {
this.arr.splice(1, 0, '新来的')
}
}
})
</script>
问题
-
DOM树是什么?----------------------就是标签关系
-
频繁操作DOM会引发什么?-------页面的重绘和回流
-
如何提高性能?-----------------------虚拟DOM
真实DOM
document对象上,渲染到浏览器上显示的标签
虚拟DOM
本质是保存节点信息、属性和内容的一个js对象
内存中虚拟DOM比较
内存中比较变化的部分,然后给真实DOM打补丁(更新)
虚拟DOM好处
提高DOM更新的性能,不频繁操作真实的DOM,在内存中找到变化的部分,更新真实的DOM(打补丁)
问题
-
新的虚拟DOM根元素,或者属性变化,如何更新?
-
具体如何比较新旧虚拟DOM?
diff算法
diff算法是通过同级比较,来比较新旧虚拟DOM
根元素变化 删除重新建立整个DOM树
根元素未变 属性改变 DOM复用 只更新属性
同级比较 ,根元素变化-整个DOM树删除重建
同级比较,根元素不变-属性改变 更新属性
标签内子标签/内容改变
diff分2种情况比较
- 无key 就地更新
- 有key 按照key比较
key值要求:唯一不重复的字符串或数值
key使用:有id用id 无id用索引
key好处:配合虚拟DOM提高更新性能
无key
从第二个往后更新内容---性能不高
有key,值为索引
有key属性,基于key来比较新旧虚拟DOM,移除key不存在元素
有key,值唯一不重复的字符串或数字
key唯一不重复
v-for不会移动DOM,而是尝试复用,就地更新,如果需要v-for移动DOM,你需要用特殊属性key来提供一个排序提示
新DOM里数据的key存在,去旧的虚拟DO结构里找到key标记的标签,复用标签
新DOM里数据的key存在,去旧的虚拟DO结构里没有找到key标记的标签,创建
旧DOM结构的key,在新的DOM结构里没有,就移除key所在的标签