Appearance
Vue3 整体变化 ✨
要点速览
- 分类:源码优化、性能优化、语法 API、RFC 流程。
- 源码:Monorepo 拆包;TypeScript 重构,类型更完善。
- 性能:响应式由
Proxy;编译期静态提升、PatchFlags、Block Tree、事件缓存、预字符串化;运行期快速 diff。 - 语法:Composition API 与
<script setup>;组合式函数替代 mixin;createApp实现应用级隔离。 - RFC:公开提案、充分讨论动机/设计/兼容性,迭代更稳健。
变化总览
Vue3 相比 Vue2 的变化可以归纳为四大维度:
- 源码工程与类型系统(Monorepo + TypeScript)
- 运行时与编译器的性能优化(响应式、编译、diff)
- 开发者 API 与编码范式(Composition API、应用创建与隔离)
- 社区协作流程(RFC 提案机制)
源码优化
源码结构(Monorepo)
- Vue2:源码集中在
src/,按功能子目录划分:compiler/core/platforms/server/sfc/shared。 - 问题:模块耦合度高,难以独立发布与版本管理;测试与类型定义难以按包隔离。
- Vue3:采用 Monorepo,将功能拆分到多个包(如
reactivity/runtime-core/runtime-dom/compiler-*),每包具备独立的 API、类型与测试。 - 收益:
- 责任边界清晰,可插拔能力更强,发布与回滚更精细。
- 用户可按需引入子包,结合 ESM 与 tree-shaking 降低最终体积。

TypeScript 重构
- 演进:Vue1 纯 JS → Vue2 使用 Flow → Vue3 全面拥抱 TypeScript。
- 优势:静态类型提升 API 设计严谨性;更佳的 IDE 自动补全与类型提示;公共类型复用与约束更一致。
- 对开发者的影响:
defineComponent/PropType等模式让组件的props/emit/slots具备良好类型推断。- 组合式 API(
ref/reactive/computed/watch)在 TS 下有明确的类型语义与约束。
性能优化
源码体积与构建
- 移除冷门特性:如
filter/inline-template等,减少运行时负担。 - 构建工具:生产环境使用 Rollup,天然偏向库构建与 ESM,利于静态分析与 tree-shaking。
- Tree-shaking:依赖于 ES 模块静态结构,移除未被引用的导出,缩减最终包体积。
js
// Vue3:从子包按需引入,利于 tree-shaking
import { ref, computed } from "vue";
// Vue2:整体引入,静态分析粒度较粗
import Vue from "vue";响应式系统
- Vue2 使用
Object.defineProperty劫持属性读写,难以覆盖新增/删除属性、数组索引与长度变化。 - Vue3 使用
Proxy劫持对象级别的访问:可感知属性新增/删除、数组操作、Map/Set等结构;覆盖更完备,性能更佳。 - 组合式 API 与响应式家族:
reactive/readonly/ref/shallowReactive/shallowRef;副作用注册与调度由effect完成。
详细内容参考文章Vue3 响应式变化
编译器优化
- 静态提升(hoistStatic):将完全静态的节点常量化,避免每次渲染重复创建。
- 预字符串化:将大文本节点在编译期拼接为常量字符串,减少运行期开销。
- 事件处理函数缓存:对不变的事件回调进行缓存,避免更新阶段的重复绑定与比较。
- Block Tree:以「可变边界」划分子树,更新时仅遍历带 PatchFlags 的可变块,缩小 diff 范围。
- PatchFlags:在编译期标记节点的可变属性,如
CLASS/STYLE/TEXT/PROPS等,使运行期能精准更新。
diff 算法
- Vue2 双端 diff:从头尾同时比较,对移动与插入场景处理较为保守。
- Vue3 快速 diff:针对有
key的子节点使用更优化的对齐策略,结合最长递增子序列(LIS)定位最少移动集,减少 DOM 操作次数。
语法 API 优化
Options API → Composition API
- Vue2 使用 Options API:将逻辑按
data/methods/computed/props分散在不同选项中。 - Vue3 推荐 Composition API:围绕「功能单元」组织相关状态与方法,读写更集中,复用粒度更细。
<script setup>:在 SFC 中以更简洁的语法使用组合式 API,编译后自动暴露到模板。

mixin → 组合式函数
- mixin 缺点:
- 数据来源不清晰(属性从何处注入难以追踪)。
- 命名冲突风险(同名属性/方法覆盖)。
- 隐式耦合(多个 mixin 之间交互难以显式表达)。
- 组合式函数:通过普通函数返回状态与方法,依赖显式传参,来源明确、可测试性更好。
js
// 组合式复用示例
function useCounter(initial = 0) {
const count = ref(initial);
const inc = () => (count.value += 1);
return { count, inc };
}应用创建与隔离(new Vue → createApp)
- Vue2 通过
new Vue()创建应用:调用构造函数的静态方法(use/mixin/component)会对页面内所有应用生效,难以实现隔离。 - Vue3 通过
createApp(root)创建应用:所有与应用相关的注册都挂在应用实例上,彼此隔离。
js
// Vue2(全局污染风险)
Vue.use(...);
Vue.mixin(...);
Vue.component(...);
new Vue({}).$mount('#app1');
new Vue({}).$mount('#app2');
// Vue3(应用级隔离)
import { createApp } from 'vue';
createApp(App).use(...).mixin(...).component(...).mount('#app1');
createApp(App).mount('#app2');面试题:为什么 Vue3 去掉了 Vue 构造函数?
- 静态方法全局生效,无法隔离多应用配置。
- 构造函数承载过多功能,不利于 tree-shaking;Vue3 以普通函数导出以便按需引入。
- 明确区分「应用」与「组件实例」两个概念;
createApp返回的是应用对象,其方法作用于整个应用,而非特殊组件。
其他重要变化
- Fragment/Teleport/Suspense 等内置能力增强组件表达力。
- 生命周期名称更新与并存。
引入 RFC
什么是 RFC
RFC(Request For Comments)是一种公开的提案流程,用于收集社区对新功能或重大更改的意见。 它以文档形式描述动机、设计、实现细节与兼容性影响,并在充分讨论后决定采纳或拒绝。
一份 RFC 通常包含
- 标题:简短描述提案目的
- 摘要:说明内容与动机
- 动机:为何需要、解决何问题
- 详细设计:核心设计与实现路径
- 潜在问题与替代方案:权衡与备选
- 不兼容变更:兼容性与迁移策略
价值与影响
- 决策透明:社区可参与功能讨论,理解取舍。
- 迭代稳健:在设计落地前充分审视边界与兼容性。
- 典型提案:Composition API、Teleport/Suspense、
<script setup>等均通过 RFC 讨论与演进。
面试题
说一下 Vue3 相比 Vue2 有什么新的变化?
参考答案:
- 源码优化:使用 TypeScript 重构核心代码,采用 Monorepo 管理多包,子包具备独立 API/类型/测试与发布能力,按需引入更容易。
- 性能优化:响应式从
Object.defineProperty升级为Proxy;编译器引入静态提升、PatchFlags、Block Tree、事件缓存、预字符串化;运行期使用更优的快速 diff 算法,整体性能显著提升。 - 语法 API:引入 Composition API 与
<script setup>,围绕功能集中组织逻辑,复用粒度更细;以组合式函数替代 mixin 的隐式注入;通过createApp提供应用级隔离,杜绝全局构造函数带来的污染。 - RFC 流程:核心团队通过 RFC 与社区协作,在公开的提案、讨论与修订中推进重大功能与变更,提升稳定性与透明度。
总结:Vue3 在工程化、性能与开发体验上进行了系统性升级。新项目推荐直接采用 Vue3,以获得更好的类型支持、更高的性能与更清晰的代码组织方式。
