vue动态渲染原理实现
Vue 动态渲染原理实现
Vue 的动态渲染核心基于响应式系统和虚拟 DOM 技术,通过数据驱动视图更新。以下是其关键实现原理:
响应式系统
Vue 使用 Object.defineProperty(Vue 2)或 Proxy(Vue 3)实现数据劫持。当数据变化时,触发依赖收集的更新通知。
// Vue 2 响应式简化实现
function defineReactive(obj, key, val) {
const dep = new Dep(); // 依赖收集器
Object.defineProperty(obj, key, {
get() {
if (Dep.target) dep.depend(); // 收集依赖
return val;
},
set(newVal) {
if (newVal === val) return;
val = newVal;
dep.notify(); // 触发更新
}
});
}
虚拟 DOM 与 Diff 算法
Vue 将模板编译为渲染函数,生成虚拟 DOM 树。数据变化时,通过 Diff 算法比对新旧虚拟 DOM,最小化真实 DOM 操作。
// 虚拟 DOM 结构示例
const vnode = {
tag: 'div',
props: { class: 'container' },
children: [
{ tag: 'p', text: '动态内容' }
]
};
模板编译
Vue 将模板编译为渲染函数,通过 with 语句和 new Function 动态生成代码:
// 模板编译结果示例
function render(_ctx) {
return _c('div', { class: _ctx.className }, [
_c('span', _ctx.message)
]);
}
异步更新队列
Vue 通过 nextTick 实现异步批量更新,避免频繁重复渲染:
// 更新队列简化实现
let queue = [];
let waiting = false;
function queueWatcher(watcher) {
queue.push(watcher);
if (!waiting) {
waiting = true;
Promise.resolve().then(flushQueue);
}
}
function flushQueue() {
queue.forEach(watcher => watcher.run());
queue = [];
waiting = false;
}
动态组件实现
通过 :is 属性和 keep-alive 实现组件动态切换:
<component :is="currentComponent"></component>
<keep-alive>
<component :is="dynamicComponent"></component>
</keep-alive>
关键技术点
- 依赖收集:每个响应式属性关联一个
Dep实例,Watcher 在求值时触发getter收集依赖 - 派发更新:数据修改时通过
setter触发Dep.notify()通知所有 Watcher - 虚拟 DOM 优化:通过同级比较和 key 复用策略提升 Diff 效率
- 编译优化:Vue 3 的静态提升和补丁标志减少运行时开销
以上机制共同实现了 Vue 高效的数据驱动视图更新能力。







