vue嵌套组件的生命周期执行顺序

975 阅读1分钟

高频面试题:Vue中嵌套组件生命周期的执行顺序是什么?

先看个例子:

const child = {
  template: `<div>child-component</div>`,
  beforeCreate() {
    console.log('child-beforeCreate')
  },
  created() {
    console.log('child-created')
  },
  beforeMount() {
    console.log('child-beforeMount')
  },
  mounted() {
    console.log('child-mounted')
  },
  beforeDestroy() {
    console.log('child-beforeDestroy')
  },
  destroyed() {
    console.log('child-destroyed')
  },
  beforeUpdate() {
    console.log('child-beforeUpdate')
  },
  updated() {
    console.log('child-updated')
  },
}

const app = {
  template: `<div @click='changeNum'><child>app-component</child><span>count:{{num}}</span></div>`,
  data() {
    return {
      num: 0,
    }
  },
  components: {
    child
  },
  beforeCreate() {
    console.log('app-beforeCreate')
  },
  created() {
    console.log('app-created')
  },
  beforeMount() {
    console.log('app-beforeMount')
  },
  mounted() {
    console.log('app-mounted')
  },
  beforeDestroy() {
    console.log('app-beforeDestroy')
  },
  destroyed() {
    console.log('app-destroyed')
  },
  beforeUpdate() {
    console.log('app-beforeUpdate')
  },
  updated() {
    console.log('app-updated')
  },
  methods: {
    changeNum() {
      this.num++;
    }
  },
}
new Vue({
  el: "#app",
  template: `<div>
    <div><app v-if="isShow"></app></div>
    <button @click='changeStaus'>切换状态</button>
  </div>`,
  data() {
    return {
      isShow: true,
    }
  },
  components: {
    app,
  },
  methods: {
    changeStaus() {
      this.isShow = !this.isShow
    },
  }
});

1、beforeCreatecreatedbeforeMountmounted

当前例子首次渲染时,打印的信息为:

image.png

执行逻辑如下所示:

image.png

从例子打印信息和图示逻辑中可以看出,beforeCreatecreatedbeforeMount的执行顺序是先父后子,而mounted是先子后父。

父组件app执行完beforeMount生命周期后,就进入了子组件child的渲染,子组件的渲染过程和父组件相似,所以又会执行一遍渲染前的生命周期beforeCrzeatecreatedbeforeMount,等到子组件组件节点渲染完成后,会执行当前子组件的mounted。子组件的渲染的渲染完成以后,当前层级的递归结束,执行逻辑交给父组件app,继续执行父组件的mounted生命周期钩子函数。

2、beforeUpdateupdated

点击父组件修改数据时,打印的信息为:

image.png

从执行打印可以看出,beforeUpdate是先父后子,updated是先子后父。

3、beforeDestroydestroyed

点击将控制父组件的显示隐藏条件为false时,打印的信息为:

image.png

从执行打印可以看出,beforeDestroy是先父父后子,destroyed是先子后父。

总结:

文中除了mountedupdateddestroyed执行顺序是先子后父,其他生命周期执行顺序是先父后子。