在 Vue 中,组件的销毁是一个重要的生命周期阶段。了解组件何时被销毁有助于更好地管理资源、避免内存泄漏以及执行清理操作。以下是 Vue 组件被销毁的常见场景:
1. 组件被移除
当组件从 DOM 中被移除时,Vue 会销毁该组件。
示例
<template>
<div>
<ChildComponent v-if="showChild"></ChildComponent>
<button @click="toggleChild">Toggle Child</button>
</div>
</template>
<script>
import ChildComponent from './ChildComponent.vue';
export default {
components: { ChildComponent },
data() {
return {
showChild: true
};
},
methods: {
toggleChild() {
this.showChild = !this.showChild;
}
}
};
</script>
说明
- 当
showChild
为false
时,ChildComponent
会被移除并销毁。
2. 路由切换
在使用 Vue Router 时,当路由切换导致当前组件不再渲染时,Vue 会销毁该组件。
示例
const routes = [
{ path: '/home', component: Home },
{ path: '/about', component: About }
];
说明
- 当从
/home
切换到/about
时,Home
组件会被销毁。
3. 动态组件切换
当使用动态组件(<component :is="...">
)时,切换组件会导致之前的组件被销毁。
示例
<template>
<component :is="currentComponent"></component>
<button @click="toggleComponent">Toggle Component</button>
</template>
<script>
import ComponentA from './ComponentA.vue';
import ComponentB from './ComponentB.vue';
export default {
data() {
return {
currentComponent: 'ComponentA'
};
},
components: { ComponentA, ComponentB },
methods: {
toggleComponent() {
this.currentComponent = this.currentComponent === 'ComponentA' ? 'ComponentB' : 'ComponentA';
}
}
};
</script>
说明
- 当
currentComponent
从ComponentA
切换到ComponentB
时,ComponentA
会被销毁。
4. 父组件被销毁
如果父组件被销毁,其所有子组件也会被销毁。
示例
<template>
<div>
<ChildComponent></ChildComponent>
<button @click="destroyParent">Destroy Parent</button>
</div>
</template>
<script>
import ChildComponent from './ChildComponent.vue';
export default {
components: { ChildComponent },
methods: {
destroyParent() {
this.$destroy(); // 销毁父组件
}
}
};
</script>
说明
- 当父组件被销毁时,
ChildComponent
也会被销毁。
5. 手动调用 $destroy
可以通过调用 $destroy
方法手动销毁组件。
示例
export default {
methods: {
destroyComponent() {
this.$destroy(); // 手动销毁组件
}
}
};
说明
- 调用
$destroy
后,组件会被销毁并触发生命周期钩子。
6. keep-alive
组件的失活
当组件被 <keep-alive>
缓存时,组件不会被销毁,而是触发 deactivated
钩子。只有当 <keep-alive>
的缓存被清除或组件被移除时,组件才会被销毁。
示例
<template>
<keep-alive>
<ChildComponent v-if="showChild"></ChildComponent>
</keep-alive>
<button @click="toggleChild">Toggle Child</button>
</template>
<script>
import ChildComponent from './ChildComponent.vue';
export default {
components: { ChildComponent },
data() {
return {
showChild: true
};
},
methods: {
toggleChild() {
this.showChild = !this.showChild;
}
}
};
</script>
说明
- 当
showChild
为false
时,ChildComponent
会被缓存,而不是销毁。 - 如果
<keep-alive>
的缓存被清除,ChildComponent
会被销毁。
7. 组件销毁的生命周期钩子
当组件被销毁时,会触发以下生命周期钩子:
beforeDestroy
:组件销毁前调用,适合执行清理操作(如清除定时器、取消订阅)。destroyed
:组件销毁后调用,此时所有子组件也已销毁。
示例
export default {
data() {
return {
timer: null
};
},
created() {
this.timer = setInterval(() => {
console.log('Timer tick');
}, 1000);
},
beforeDestroy() {
clearInterval(this.timer); // 清除定时器
},
destroyed() {
console.log('Component destroyed');
}
};
总结
Vue 组件会在以下情况下被销毁:
- 组件被移除:如
v-if
条件为false
。 - 路由切换:当前组件不再渲染。
- 动态组件切换:切换到其他组件。
- 父组件被销毁:父组件销毁时,子组件也会被销毁。
- 手动调用
$destroy
:主动销毁组件。 keep-alive
缓存被清除:当缓存被清除或组件被移除时。
在组件销毁时,可以通过 beforeDestroy
和 destroyed
钩子执行清理操作,避免内存泄漏。
THE END
暂无评论内容