$parent访问直接父组件实例,$root访问根Vue实例;二者均属非推荐的直接引用方式,适用于调试或轻量全局操作,但破坏封装性、类型安全差,应优先使用props/$emit、provide/inject或Pinia。

在 Options API 中,$parent 和 $root 是 Vue 提供的实例属性,用于在父子组件树中向上访问上级组件实例。它们不依赖 props 或 events,属于直接引用方式,适用于特定调试、快速原型或极简场景,但不推荐作为常规通信手段。
$parent:访问直接父组件实例
子组件可通过 this.$parent 获取其紧邻的父组件实例,从而读取数据、调用方法或访问计算属性。
使用前提:
- 父组件必须已定义对应的数据或方法(非私有);
- 子组件需在
mounted或后续生命周期中访问(避免created阶段父组件尚未完成初始化)。
示例(子组件中):
export default {
mounted() {
console.log(this.$parent.msg); // 读取父组件 data 中的 msg
this.$parent.updateCounter(); // 调用父组件 methods 中的方法
},
methods: {
triggerParentAction() {
if (this.$parent && typeof this.$parent.notify === 'function') {
this.$parent.notify('来自子组件的消息');
}
}
}
}⚠️ 注意:
-
$parent是只读属性,不能赋值; - 破坏封装性,父组件结构变动(如加中间层)会导致子组件失效;
- TypeScript 下无类型提示,需手动声明父组件类型(如
@ts-ignore或defineComponent显式泛型)。
$root:访问整个应用的根 Vue 实例
this.$root 指向通过 new Vue({ ... }) 创建的顶层实例(Vue 2)或 createApp(App).mount(...) 的根应用实例(Vue 3 兼容模式下仍保留该属性)。它在整个组件树中唯一且稳定。
常见用途:
- 全局状态轻量共享(如主题、语言、登录态);
- 全局事件总线(
this.$root.$emit/this.$root.$on); - 调试时快速查看/触发根级逻辑。
示例(任意深层子组件中):
export default {
methods: {
toggleTheme() {
// 直接调用根实例方法
this.$root.toggleDarkMode();
},
emitGlobalEvent() {
// 发布全局事件
this.$root.$emit('user-logout', { timestamp: Date.now() });
}
}
}✅ 根实例需提前暴露能力(如在 main.js 中):
// main.js(Vue 2 或 Vue 3 兼容写法)
const app = new Vue({
el: '#app',
data: { theme: 'light' },
methods: {
toggleDarkMode() {
this.theme = this.theme === 'light' ? 'dark' : 'light';
}
}
});⚠️ 注意:
-
$root在 Vue 3 Composition API +<script setup></script>中依然可用,但更推荐provide/inject或 Pinia; - 不适合高频响应式更新场景——
$root上的响应式数据不会自动触发子组件更新(除非显式watch或绑定到模板); - 多个根应用共存时(如微前端),
$root只指向当前挂载的根,非全局唯一。
对比与建议
| 特性 | $parent |
$root |
|---|---|---|
| 访问目标 | 直接父组件 | 整个应用的根 Vue 实例 |
| 稳定性 | 低(父组件变更即断) | 高(根实例生命周期内不变) |
| 类型安全 | 差(无自动推导) | 差(需手动注解) |
| 推荐程度 | ❌ 仅限临时调试或内部工具组件 | ⚠️ 仅限轻量全局行为,避免业务核心逻辑 |
更健壮的替代方案:
- 父 → 子:用
props+v-model;- 子 → 父:用
$emit或defineEmits;- 跨多层:用
provide / inject;- 全局状态:用 Pinia 或 Vuex。
不复杂但容易忽略。


















