vue中computed实现原理
Vue中computed的实现原理
computed属性是Vue的核心特性之一,它基于响应式依赖进行缓存,仅在相关依赖发生改变时才会重新计算。
依赖收集与缓存机制
computed属性通过Object.defineProperty或Proxy(Vue 3)定义在组件实例上。初始化时创建一个Watcher实例,设置lazy标志为true表示惰性求值。
当首次访问computed属性时,会执行getter函数并触发依赖收集。Vue的响应式系统会记录哪些响应式数据被访问过,建立依赖关系。计算结果的缓存存储在Watcher实例的value属性中。

惰性更新策略
后续访问computed属性时,若依赖未变化则直接返回缓存值。当依赖数据发生变化时,标记computed为"dirty"状态,但不会立即重新计算。直到下次访问该属性时才会执行实际计算,这种延迟更新机制优化了性能。
与watch的区别
computed自动追踪依赖关系,而watch需要显式指定监听目标。computed适合派生状态,watch适合执行副作用操作。computed具有缓存特性,watch每次触发都会执行回调。

源码层面的关键实现
Vue 2.x版本中核心实现位于src/core/instance/state.js:
function initComputed(vm, computed) {
const watchers = vm._computedWatchers = Object.create(null)
for (const key in computed) {
const getter = typeof computed[key] === 'function'
? computed[key]
: computed[key].get
watchers[key] = new Watcher(
vm,
getter || noop,
noop,
{ lazy: true }
)
defineComputed(vm, key, userDef)
}
}
Vue 3使用computed函数和effect实现,基于Proxy的响应式系统:
function computed(getterOrOptions) {
let getter, setter
if (isFunction(getterOrOptions)) {
getter = getterOrOptions
setter = NOOP
} else {
getter = getterOrOptions.get
setter = getterOrOptions.set
}
return new ComputedRefImpl(getter, setter)
}
性能优化要点
避免在computed中进行高开销操作,确保纯函数特性。合理设计依赖关系,防止不必要的重新计算。对于复杂计算可考虑使用memorization技术进一步优化。






