虚拟dom diff算法

引入

需求:有一个变量 count 的初始值时 0,经过一系列运算,得到10001,然后将结果写入box中

<div class="box"></div>

var box = document.querySelector( '.box' )
var count = 0 ;

console.time( 'a' )
for( var i = 0 ; i < 10001 ; i++ ){
count ++
box.innerHTML = count
}
console.timeEnd( 'a' ) // a字符输出花费的时间

// 我们肯定会这么写
count = 0
console.time( 'b' )
for( var i = 0 ; i < 10001 ; i++ ){
count ++
}


box.innerHTML = count


console.timeEnd( 'b' )

对比以上 a b 输出花费的时间,得出的结论:

更少的dom操作会更加减少 时间花费 减少性能损耗

我们应该先 操作数据 再去操作dom

由以上结论慢慢的前端将一个 概念引入在 框架中 虚拟dom

虚拟dom是什么(virtual dom)?

它是一个Object对象模型,用来模拟真实dom节点的结构

需求: vdom如何模拟真实dom,如果将来我想在增加一个li,里的内容为 : 这里是千锋教育 再增加10个li,内容为: xxx

真实dom写法:

<div class = "box">
<ul>
<li> hello </li>
</ul>
</div>


var list = document.querySelector( '.list' )
var li = document.createElement( 'LI' )
li.innerHTML = ' 你好 '


list.appendChild( li )

vdom的使用教程

1.获取数据( ajax fetch )这里是模拟数据

var data = {
id: 1,
name: '张三'
}

2.创建vdom

<div class = "box">
<ul>
<li> {{ data.name }} </li>
</ul>
</div>

3.通过render函数解析jsx,将其转换成 vdom结构

真实dom写法:

var div = document.createElement('DIV')
div.className = 'box'
var ul = document.createElement('UL')
var li = document.createElement('LI')

vue中使用的是一个叫做jsx语法 + render函数

jsx语法出现的原因:

由于网页结构一般都是很复杂的,这时我们使用vdom去模拟dom结构,发现vdom这个对象模型太大了,也长了,所以我们想,如果能在js中也能够书写 dom标签结构那就好了,所以结合了javascript + xml ( js中也能写html结构 )搞出了一个新的语法糖 jsx ,用jsx来模拟vdom

通过render函数解析jsx,将其转换成 vdom结构

var vdom = {
tag: 'div',
attr: {
className: 'box'
},
content: [
{
tag: 'ul',
content: [
{
tag: 'li',
content: data.name
}
]
}
]
}

4.将vdom渲染成真实dom
render函数

5.数据更改了, data.name = ‘zhangsan’

data.name = 'zhangsan'

vdom = {
tag: 'div',
attr: {
className: 'box'
},
content: [
{
tag: 'ul',
content: [
{
tag: 'li',
content: data.name
}
]
}
]
}

6.使用diff算法比对两次vdom,生成patch对象

diff算法是比较两个文件的差异,并将两个文件不同之处,将这个不同之处生成一个补丁对象(patch)

diff算法来源后端

前端将其应用于虚拟dom的diff算法

vue中将 虚拟dom的diff算法放在了 patch.js文件中
使用js来进行两个对象的比较( vdom 对象模型)

diff算法是同级比较
给每一个层级打一个标记,这个标记是一个数字( 这个数字就是 key )

7.根据key将patch对象渲染到页面中改变的结构上,而其他没有改变的地方是不做任何修改的( 虚拟dom的惰性原则 )

补充: vue的key的作用
id 为app的dom结构其实是一个模板,其实就是jsx

案例: 以一个案例来说明key是用来做标识的( 同级比较 )

<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>
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 )
}
}
})
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值