返回

Vue响应式原理

前端




Vue响应式原理

Vue2的响应式原理

Vue2的响应式原理是通过Object.defineProperty()来实现的。Object.defineProperty()可以对对象的属性进行劫持,当属性发生变化时,会触发getter或setter函数。Vue2中,通过Object.defineProperty()对对象的每个属性进行劫持,当属性发生变化时,会触发getter函数,getter函数会将属性的值传递给watcher,watcher会将属性的值保存起来。当组件重新渲染时,watcher会将属性的值传递给组件,组件就会更新视图。

Vue3的响应式原理

Vue3的响应式原理是通过Proxy来实现的。Proxy可以对对象进行代理,当对象发生变化时,会触发Proxy的handler函数。Vue3中,通过Proxy对对象进行代理,当对象发生变化时,会触发Proxy的handler函数,handler函数会将属性的值传递给watcher,watcher会将属性的值保存起来。当组件重新渲染时,watcher会将属性的值传递给组件,组件就会更新视图。

Vue2和Vue3的响应式原理对比

Vue2和Vue3的响应式原理都是通过劫持对象属性来实现的,但是Vue2使用的是Object.defineProperty(),而Vue3使用的是Proxy。Object.defineProperty()只能劫持对象的自身属性,而Proxy可以劫持对象的自身属性和继承属性。此外,Proxy还支持拦截对象的操作,比如delete、set等。

Vue响应式原理的源码实现

Vue2的响应式原理源码实现

Vue2的响应式原理源码实现位于src/core/observer/index.js文件中。

export function defineReactive (obj, key, val) {
  const dep = new Dep()
  Object.defineProperty(obj, key, {
    get: function reactiveGetter () {
      dep.depend()
      return val
    },
    set: function reactiveSetter (newVal) {
      if (newVal !== val) {
        val = newVal
        dep.notify()
      }
    }
  })
}

Vue3的响应式原理源码实现

Vue3的响应式原理源码实现位于src/reactivity/reactive.js文件中。

export function reactive (target) {
  return createReactiveObject(
    target,
    {},
    {},
    proxyHandlers,
    true /* isReactive */
  )
}

const proxyHandlers = {
  get (target, key, receiver) {
    track(target, key)
    return Reflect.get(target, key, receiver)
  },
  set (target, key, value, receiver) {
    const oldValue = target[key]
    const result = Reflect.set(target, key, value, receiver)
    if (oldValue !== value) {
      trigger(target, key, value)
    }
    return result
  }
}

总结

Vue的响应式原理是Vue框架的核心原理之一。Vue2和Vue3的响应式原理都是通过劫持对象属性来实现的,但是Vue2使用的是Object.defineProperty(),而Vue3使用的是Proxy。Proxy可以劫持对象的自身属性和继承属性,还可以拦截对象的操作,比如delete、set等。Vue的响应式原理使Vue框架能够高效地更新视图,从而提高了Vue框架的性能。