目录
2.1 computed 和 watch 的区别和运用的场景
一、组件间通信
Vue组件间通信:
- props / $emit:这个一般用于父子组件之间的通信,父组件通过 props 的方式向子组件传递数据,子组件可以通过 $emit 的方式向父组件进行通信。
- $parent / $children:通过 $parent 和 $children 就可以访问到对应组件的实例,既然都访问到组件实例了,那么组件内的所有内容(data、methods等)就都能够访问到了
- ref:如果在普通的 DOM 元素上使用,引用指向的就是 DOM 元素;如果用在子组件上,引用就指向组件实例
- eventBus(事件总线,即$emit / $on):eventBus 又称为事件总线,在vue中可以使用它来作为沟通桥梁的概念, 就像是所有组件共用相同的事件中心,可以向该中心注册发送事件或接收事件, 所以组件都可以通知其他组件。使用 $on 订阅事件,$emit 发布事件
- $attr / $listeners:在vue2.4中,为了解决使用props与emit来通信需将数据层层下传的问题,引入了$attrs 和 $listeners , 新增了inheritAttrs 选项。
- provide / inject:provide / inject 是vue2.2.0新增的api, 简单来说就是父组件中通过 provide 来提供变量, 然后再子组件中通过 inject 来注入变量。并且不论子组件嵌套有多深, 只要调用了 inject 那么就可以注入 provide 中的数据
- vuex:Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。适用于父子、隔代、兄弟组件通信。
1.1 父子组件间通信
- props / $emit
- $parent / $children
- ref
- eventBus(事件总线,即$emit / $on)
- $attr / $listeners
- provide / inject
- vuex
1.2 兄弟组件间通信
- eventBus
- vuex
1.3 跨级组件间通信
- eventBus
- vuex
- provide / inject
- $attr / $listeners
1.4 怎么理解Vue的单向数据流
在Vue中,所有的 prop 都使得其父子 prop 之间形成了一个 单向数据流:父级prop的更新会向下传到子组件中,但反过来不行。
也就是说数据总是从父组件传到子组件,且子组件没有权利修改父组件传过来的数据,只能请求父组件对原始数据进行修改。
所以每次父级组件发生更新时,子组件中所有的 prop 都将会刷新为最新的值,子组件想修改时,只能通过 $emit 派发一个自定义事件,父组件接收到后,由父组件修改。
二、computed 和 watch 相关
2.1 computed 和 watch 的区别和运用的场景
computed:
- 计算属性,依赖其他属性值。
- computed 的值有缓存,只有依赖的属性值发生改变时,下次获取 computed 的值才会重新计算 computed。
- computed 不支持异步。
- 必须调用return
watch:
- 更多的是观察作用,类似于某些数据的侦听回调,每当侦听的数据变化时都会执行回调进行后续操作
- watch不支持缓存,数据变化时会立即执行回调
- watch支持异步
运用的场景:
- watch擅长处理的场景:一个数据影响多个数据
- computed擅长处理的场景:一个数据受多个数据影响
三、Vue2最低兼容到IE几?
vue2兼容IE8以上版本,IE8及以下版本不支持 Object.defineProperty 方法,但这个是vue实现响应式的所必须的
四、数据响应式原理
4.1 vue2.x的响应式
实现原理:
- 对象类型:通过 Object.defineProperty() 对属性的读取、修改进行拦截(数据劫持)
- 数组类型:通过重写更新数组的一系列方法来实现拦截。(对数组的变更方法进行了包裹)
存在问题:
- 新增属性、删除属性,界面不会刷新
- 直接下标修改数组,界面不会自动属性
问题解决:
- Vue.set(target, propertyName/index, value)
- vm.$set(target, propertyName/index, value)
4.2 Vue3.0的响应式
实现原理:
- 通过 Proxy(代理): 拦截对象中任意属性的变化, 包括:属性值的读写、属性的添加、属性的删除等。
- 通过 Reflect(反射): 对源对象的属性进行操作
4.3 Vue2与Vue3的数据响应式原理有什么区别
Vue2 中的响应式对 Object 及 Array 分别进行了不同的处理,Object 使用了 Object.defineProperty API,Array 使用了拦截器对 Array 原型上的能够改变数据的方法进行拦截。虽然也实现了响应式,但存在很多问题 ,比如对象新增属性无法被侦测,以及通过数组下标修改数组内容,也因此在 Vue2 中经常会使用到 $set 方法对数据修改,以保证更新。
Vue3 中使用了 es6 的 Proxy API 对数据代理,没有像 Vue2 中对原数据进行修改,只是加了代理包装,因此首先性能上会有所改善。其次解决了 Vue2 中响应式的局限性,可以不使用 $set 新增的对象属性及通过下标修改数组都能被侦测到。