以下是 Vue 2 和 Vue 3 生命周期的对比总结,结合代码示例和示意图,帮助新手快速理解核心差异:
📊 一、生命周期钩子对照表(Vue 2 → Vue 3)
| Vue 2 钩子 | Vue 3 钩子 | 触发时机 | 关键变化 |
|---|---|---|---|
beforeCreate | setup() 替代 | 组件实例初始化前,数据未响应式 | Vue 3 中 beforeCreate/created 被 setup() 替代,无需显式定义 |
created | setup() 替代 | 数据响应式完成,可访问 data/methods | |
beforeMount | onBeforeMount | DOM 挂载前,编译模板完成,虚拟 DOM 已创建 | Vue 3 钩子需通过 import { onXxx } from 'vue' 引入 |
mounted | onMounted | DOM 挂载完成,可操作 DOM 或发起请求 | 功能一致,名称增加 on 前缀 |
beforeUpdate | onBeforeUpdate | 数据更新后,DOM 重新渲染前 | |
updated | onUpdated | DOM 更新完成,避免在此修改数据 | |
beforeDestroy | onBeforeUnmount | 组件销毁前,可清理定时器/事件 | 名称更语义化(Unmount 替代 Destroy) |
destroyed | onUnmounted | 组件销毁后,所有子实例被移除 |
💡 记忆口诀:
“Vue 3 钩子加on,创建阶段变setup,销毁改名Unmount”
唯一新增钩子:onRenderTracked(调试响应式依赖)和onRenderTriggered(调试重新渲染)。
🔄 二、执行顺序对比
Vue 2 顺序
beforeCreate → created → beforeMount → mounted → beforeUpdate → updated → beforeDestroy → destroyed
Vue 3 顺序
setup() → onBeforeMount → onMounted → onBeforeUpdate → onUpdated → onBeforeUnmount → onUnmounted
⚠️ 注意:
setup()在beforeCreate前执行,是组合式 API 的入口。
🧩 三、代码示例对比
Vue 2(Options API)
export default {
data() {
return { count: 0 };
},
created() {
console.log("数据已响应式,可请求接口");
},
mounted() {
console.log("DOM 已挂载");
},
beforeDestroy() {
console.log("清理定时器");
}
};
Vue 3(Composition API)
import { onMounted, onUnmounted, ref } from 'vue';
export default {
setup() {
const count = ref(0);
// 替代 created 的逻辑
console.log("数据初始化完成");
onMounted(() => {
console.log("DOM 已挂载");
});
onUnmounted(() => {
console.log("组件卸载,清理资源");
});
return { count };
}
};
✅ 优势:同一功能的逻辑集中写在
setup()中,避免分散到不同钩子。
🧠 四、新手常见疑问解答
-
为何 Vue 3 移除
beforeCreate/created?
setup()已涵盖二者的功能:初始化数据、方法、请求等,简化设计。 -
为什么钩子名称改为
onXxx?
统一组合式 API 的命名规范,且on前缀更符合函数式编程习惯。 -
Vue 3 是否兼容 Vue 2 的钩子?
是!Options API 仍支持旧钩子(如mounted),但组合式 API 需改用onMounted。 -
setup()中能使用this吗?
不能!setup()在组件实例创建前执行,this为undefined。
⚙️ 五、迁移指南(Vue 2 → Vue 3)
| 场景 | 操作 |
|---|---|
| 初始化逻辑 | 从 created 移至 setup() 内部 |
| DOM 操作 | 从 mounted 改为 onMounted |
| 资源清理 | 从 beforeDestroy 改为 onBeforeUnmount |
| 响应式数据声明 | 用 ref() 或 reactive() 替代 data() |
| 多个根节点模板 | 直接使用 Fragment(无需外层 <div>) |
💎 六、总结:核心差异图示
Vue 2 生命周期流:
创建 → 挂载 → 更新 → 销毁
│ │ │ │
└─Options API │ └─名称固定
└─逻辑分散
Vue 3 生命周期流:
setup() → 挂载 → 更新 → 卸载
│ │ │ │
└─逻辑集中 │ └─钩子带 `on`
└─支持 Fragment/Teleport
✨ 一句话理解:
Vue 3 通过setup()整合创建阶段,钩子函数化(加on前缀),命名更语义化(Unmount替代Destroy),同时保留 Options API 兼容性。