1.Vue的绑定原理:其实就是 new Vue的原理
(1).先创建一个vue类型的子对象
a.引入data对象:
1). 自动为data对象中每个变量都请了保镖(访问器属性)!
结果: 任何位置访问data中的变量时,其实根本就不是直接访问data中变量,仅仅访问的是为data中的变量请的同名保镖而已
结果: 只要外界试图修改data中的变量时,注定会触发保镖的set()方法。
2). new Vue()还自动在每个变量的set()函数内植入了一个通知函数
结果: 只要外界试图修改data中的变量时,注定会触发保镖的set()方法中的通知函数。整个vue框架就知道一个变量的值被修改了!
b.引入并打散methods对象:
1). Methods中所有函数默认直接隶属于new Vue()对象
2). 导致methods中的函数进入new Vue()后和data中变量的保镖(访问器属性)平级
3). 所以,methods中的方法想访问data中的变量,必须加this.变量名
(2).构建虚拟DOM树:
a.什么是虚拟DOM树
通过扫描完整版DOM树创建出的一棵新DOM树
b.过程
1). new Vue()会查找到el属性指定的界面上的父元素
2). 扫描找到的父元素及其子元素
3). 碰到"@事件名=函数名",就自动翻译为on事件名=函数名——自动绑定事件
4). 碰到所有"{{变量名}}":
i. 先将可能变化的元素对象加入到虚拟DOM树中
ii. 并且首次替换元素内容中{{变量名}}为变量的初始值
(3)结果
每次只要data中的变量被修改时:
a. 自动调用变量的set()函数
b. set()中内置的通知函数向vue框架发出通知,说xx变量发生了改变
c. 框架会自动扫描虚拟DOM树
d. 查找受本次变量修改影响的所有DOM元素
e. 自动利用已经提前封装好的DOM增删改查操作,只更新页面上受影响的元素。其他不受该变量影响的元素,保持不变!
(4)总结
1.VUE绑定原理
访问器属性+虚拟DOM树
访问器属性+观察者模式+虚拟DOM
2.虚拟DOM树的优点
(1). 内容少!仅保存可能变化的元素。不变的元素一个都不包含
(2). 遍历快!
(3). 避免大量重复代码!——自动执行DOM增删改查操作
(4). 效率高!每次变量更改时,只修改个别受影响的元素,其他元素保持不变!
观察者模式
当一个变量值被修改时,可以自动通知所有关注这个变量的其他对象,让他们自动重新获得这个变量的新值
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
</head>
<body>
<script>
//观察者(observer)模式: 当一个变量值被修改时,可以自动通知所有关注这个变量的其他对象,让他们自动重新获得这个变量的新值。
var data={
money:1000,
setMoney(money){
this.money=money;
//只要money被修改,就要调用notifyAll()
this.notifyAll();
},
observers:[],
notifyAll(){
this.observers.forEach(function(obj){
obj.getMoney() //要求,凡是进入observers数组中的对象,必须自身携带一个getMoney()函数,表示自己是关注money变化的
})
}
}
var obj1={
money:0,
getMoney(){
console.log(`obj1得知data的money被改为${data.money},并重新获得data.money`);
this.money=data.money;
}
}
var obj2={
money:0,
getMoney(){
console.log(`obj2得知data的money被改为${data.money},并重新获得data.money`);
this.money=data.money;
}
}
var obj3={
money:0,
getMoney(){
console.log(`obj3得知data的money被改为${data.money},并重新获得data.money`);
this.money=data.money;
}
}
data.observers.push(obj1);
data.observers.push(obj2);
data.observers.push(obj3);
data.setMoney(900);
console.log(obj1.money, obj2.money, obj3.money)
data.setMoney(800);
console.log(obj1.money, obj2.money, obj3.money)
</script>
</body>
</html>