虚拟DOM
1.虚拟DOM是什么?
它是一个Object对象模型,用来模拟真实dom节点的结构
2.虚拟DOM的基本使用流程
-
获取数据(ajax fetch)
var data = { id: 1, name: 'bbb' }
-
创建vdom
/* <div class = "box"> <ul> <li> {{ data.name }} </li> </ul> </div> */
-
通过render函数解析jsx,将其转换成 vdom结构
var vdom = { tag: 'div', attr: { className: 'box' }, content: [ { tag: 'ul', content: [ { tag: 'li', content: data.name } ] } ] }
-
将vdom渲染成真实dom (reader函数)
-
数据更改了, data.name = ‘更改后的数据’
data.name = 'aaa' vdom = { tag: 'div', attr: { className: 'box' }, content: [ { tag: 'ul', content: [ { tag: 'li', content: data.name } ] } ] }
-
使用diff算法比对两次vdom,生成patch对象
-
根据key将patch对象渲染到页面中改变的结构上,而其他没有改变的地方是不做任何修改的( 虚拟dom的惰性原则 )
3.什么是jsx
javascript + xml
diff运算
1.diff运算是什么?
diff算法是比较两个文件的差异,并将两个文件不同之处,将这个不同之处生成一个补丁对象(patch)
2.diff算法运行结束之后,返回什么?
补丁对象(patch)
3.diff的比较方式
同层级比较:
给每一个层级打一个标记,这个标记是一个数字( 这个数字就是 key )
4.验证key
-
列表循环一定加key
-
key最好是使用具有唯一标识性的 id
<div id="app"> <ul> <li v-for = " (item,index) in list" :key = "item.id"> <p> {{ item.text }} </p> <div> <button @click = "changeStyle"> 修改样式 </button> <button @click = "remove( index )">删除 </button> </div> </li> </ul> </div>
案例: 以一个案例来说明key是用来做标识的( 同级比较 ) new Vue({ el: '#app', data: { list: [ { id: 1, text: '敲代码1' }, { id: 2, text: '敲代码2' } ] }, methods: { changeStyle ( e ) { //这段代码只是为了看key的作用,这段代码在实际情况下不能出现, // 理由: 应该避免操作真实dom e.target.parentNode.parentNode.style.background = 'red' }, remove ( index ) { this.list.splice( index, 1 ) } } })
5.为什么列表循环要加key?
跟踪每个节点的身份,从而重用和重新排序现有元素
需要使用key来给每个节点做一个唯一标识,区分层级,才能同层级比较