前言
双向数据绑定是Vue的重要原理,也是面试过程中几乎必问的一道题目,搞懂这个原理无论是对我们的技术提高还是对面试都是有百利而无一害的,下面就让我们一起来解决这个问题吧~
双向数据绑定每一个模块都负责什么?
new Vue
new Vue这个操作主要是调用了数据劫持Observe方法和模板编译的函数Compile。
Observe函数
Observer函数将递归遍历传入对象的所有property,并使用Object.defineProperty把这些property全部转化为getter/setter。一旦监听的属性发生变化的时候变通知Dep类。
Dep类
Dep类负责收集每个watcher,并当Observe监听到属性变化时通知收集到的每一个watcher。
Watcher类
Watcher是Observe和Compile之间的桥梁,watcher会在自身实例化的时候向dep类上添加自身,并提供一个update方法,一旦属性发生变化时,dep类会通过这个方法来触发Compile中的回调函数进行渲染数据。
Compile函数
Compile函数的主要工作是将模板中的变量替换成数据,然后渲染页面视图,并给每个节点绑定更新函数,创建订阅者,一旦数据有变化,收到通知就更新视图,因为遍历的时候会多次操作DOM,为了提高效率会将根节点转换成文档碎片fragment进行离线DOM操作,解析完成之后再将fragment添加到真实的DOM中。
双向数据绑定原理流程图
Vue2和Vue3响应式原理的不同之处
- Vue2使用的是Object.defineProperty()实现响应式原理,而Vue3使用的是Proxy()实现。
- 在面对对象嵌套的时候,Vue2和Vue3都需要进行递归,但是Vue2是对所有属性进行递归,而Vue3则是按需递归,如果没有使用到内部对象的属性,就不要递归,性能更好。
- Vue2中对象不存在的属性是不能被拦截的,但是Vue3可以。
Vue3为什么弃用了ObjectdefineProperty选择了Proxy
- Object.defineProperty无法监控到数组下标的变化,导致通过数组数组下标添加元素不能实时响应。
- Proxy不仅可以代理对象,还可以代理数组,还可以代理动态增加的属性。
- Object.defineProperty不能对ES6新产生的Map、Set这样的数据结构进行监听。
总结
在回答关于双向数据绑定的问题的时候,可以结合上面的流程图,对每一个节点主要的工作进行介绍,并把流程讲清楚即可。