zerojs前端面试题系列--vue3篇(2)

1. 请说说Vue的生命周期,和vue2的有什么区别?

Vue 的生命周期可以分为8个阶段:创建前后、挂载前后、更新前后、销毁前后,以及一些特殊场景的生命周期。Vue 3 中还新增了是3个用于调试和服务端渲染的场景。

Vue 2中的生命周期钩子 Vue 3选项式API的生命周期选项 Vue 3 组合API中生命周期钩子 描述
beforeCreate beforeCreate setup() 创建前,此时datamethods的数据都还没有初始化
created created setup() 创建后,data中有值,尚未挂载,可以进行一些Ajax请求
beforeMount beforeMount onBeforeMount 挂载前,会找到虚拟DOM,编译成Render
mounted mounted onMounted 挂载后,DOM已创建,可用于获取访问数据和DOM元素
beforeUpdate beforeUpdate onBeforeUpdate 更新前,可用于获取更新前各种状态
updated updated onUpdated 更新后,所有状态已是最新
beforeDestroy beforeUnmount onBeforeUnmount 销毁前,可用于一些定时器或订阅的取消
destroyed unmounted onUnmounted 销毁后,可用于一些定时器或订阅的取消
activated activated onActivated keep-alive缓存的组件激活时
deactivated deactivated onDeactivated keep-alive缓存的组件停用时
errorCaptured errorCaptured onErrorCaptured 捕获一个来自子孙组件的错误时调用
--- renderTracked onRenderTracked 调试钩子,响应式依赖被收集时调用
--- renderTriggered onRenderTriggered 调试钩子,响应式依赖被触发时调用
--- serverPrefetch onServerPrefetch 组件实例在服务器上被渲染前调用

父子组件的生命周期执行顺序:

  • 加载渲染阶段:父 beforeCreate -> 父 created -> 父 beforeMount -> 子 beforeCreate -> 子 created -> 子 beforeMount -> 子 mounted -> 父 mounted
  • 更新阶段:父 beforeUpdate -> 子 beforeUpdate -> 子 updated -> 父 updated
  • 销毁阶段:父 beforeDestroy -> 子 beforeDestroy -> 子 destroyed -> 父 destroyed

在Vue.js中,组件的生命周期可以分为加载渲染阶段、更新阶段和销毁阶段。下面是对每个阶段的优化的详细说明:

加载渲染阶段优化:

  • 在父组件的beforeCreatecreated阶段,可以进行一些初始化工作,例如设置初始数据、引入必要的插件等。
  • 在父组件的beforeMount阶段,可以在DOM挂载之前进行一些准备工作,例如获取远程数据、计算属性等。
  • 在子组件的beforeCreatecreated阶段,可以进行一些子组件的初始化操作,例如设置子组件的初始状态、注册事件等。
  • 在子组件的beforeMount阶段,可以在DOM挂载之前进行一些子组件的准备工作,例如计算子组件的样式、绑定事件等。
  • 在子组件的mounted阶段,可以进行一些与DOM相关的操作,例如操作DOM元素、启动定时器等。
  • 在父组件的mounted阶段,可以进行一些与整个组件相关的操作,例如监听事件、发送请求等。

更新阶段优化:

  • 在父组件的beforeUpdate阶段,可以在更新之前进行一些准备工作,例如保存一些需要保持的数据、做一些计算等。
  • 在子组件的beforeUpdate阶段,可以在更新之前进行一些子组件的准备工作,例如更新子组件的状态、计算子组件的样式等。
  • 在子组件的updated阶段,可以进行一些与DOM相关的操作,例如操作DOM元素、更新样式等。
  • 在父组件的updated阶段,可以进行一些与整个组件相关的操作,例如重新计算属性、发送请求等。

销毁阶段优化:

  • 在父组件的beforeDestroy阶段,可以进行一些清理工作,例如取消事件监听、销毁定时器等。
  • 在子组件的beforeDestroy阶段,可以进行一些子组件的清理工作,例如解绑事件、释放资源等。
  • 在子组件的destroyed阶段,可以进行一些与DOM相关的操作,例如移除DOM元素、清空缓存等。
  • 在父组件的destroyed阶段,可以进行一些与整个组件相关的操作,例如释放内存、取消请求等。

2. 在Vue3应该如何使用Composition API?

Vue3.x的Composition API可以让开发者更灵活地组合和封装逻辑代码。使用Composition API需要先在component中调用setup()函数,这个函数会在component创建前被调用。之后,在setup()函数中,你可以使用新的reactive()函数来创建响应式数据对象,使用computed()函数来创建计算属性,使用watch()函数来监听数据变化等等。

javascript 复制代码
import { reactive, computed, watch } from 'vue';

export default {
  setup() {
    const state = reactive({
      count: 0,
    });

    const doubleCount = computed(() => state.count * 2);

    watch(
      () => state.count,
      (newCount, oldCount) => {
        console.log(`state.count changed from ${oldCount} to ${newCount}`);
      }
    );

    function increment() {
      state.count++;
    }

    return {
      state,
      doubleCount,
      increment,
    };
  },
};

3. 在Vue3 中 computed 属性是如何工作的?它和一个函数方法有什么不同?

在Vue3中,computed属性仍然是一个函数,但是它的定义方式有所不同,可以使用 computed() 函数进行定义。

和一个普通的函数方法相比,computed属性的主要不同在于它具有缓存功能。当computed属性依赖的响应式数据发生变化时,computed函数会重新执行,但是在下一次访问computed属性时,会直接返回上一次执行的结果,而不是重新计算一遍。

例如,下面是一个计算税收的computed属性的示例:

js 复制代码
import { computed, reactive } from 'vue'

const state = reactive({
  price: 100,
  taxRate: 0.1
})

const totalPrice = computed(() => {
  return state.price * (1 + state.taxRate)
})

console.log(totalPrice.value) // 110

state.price = 200

console.log(totalPrice.value) // 220

此外,computed属性也有一些其他的特点:

  1. computed属性必须返回一个值,而不能有副作用。computed属性只能用于计算数据(即根据已有的响应式数据计算出一个新的值),而不能在computed属性中直接修改其他响应式数据或引起其他副作用。
  2. computed属性可以被设置为只读或可写,如果需要在computed属性中修改其他响应式数据,可以使用 getset 方法。在定义computed属性时,可以通过设置get和set方法来控制computed属性的只读或可写状态,并且可以在set方法中修改其他响应式数据。
html 复制代码
<template>
  <div>
    <p>Product name: {{productName}}</p>
    <button @click="updateProductName">Update</button>
  </div>
</template>

<script>
  import { computed, reactive } from "vue";

  export default {
    setup() {
      const data = reactive({
        count: 0,
        name: "Product"
      });

      const productName = computed({
        get() {
          return data.name + " " + data.count;
        },
        set(value) {
          [data.name, data.count] = value.split(" ");
        }
      });

      function updateProductName() {
        productName.value = "New Product 1";
      }

      return {
        productName,
        updateProductName
      };
    }
  };
</script>

4. 解释一下 Vue3中的 watch 和 watchEffect 的区别和用法。

Vue3中的 watchwatchEffect 都是用于监听数据变化的方法,但是二者的用法和实现方式略有不同。

watch是Vue2中的一个API,在Vue3中也有保留并进行了一些优化,它可以监听指定的数据变化,并执行对应的回调函数。 watch 接收两个参数,第一个参数是需要监听的数据,可以是一个函数,返回需要监听的数据值;第二个参数是回调函数,当监听的数据发生变化时,回调函数被调用。watch的代码示例如下:

js 复制代码
const state = Vue.reactive({ count: 0 })
Vue.watch(() => state.count, (newVal, oldVal) => {
  console.log(`count变化了:${oldVal} -> ${newVal}`);
})
state.count++ // 在控制台输出:'count变化了:0 -> 1'

watchEffect (API新增)是基于 reactive 实现的自动侦测响应式依赖的函数,其内部会自动收集响应式数据的依赖,当依赖发生变化时,自动重新执行回调函数并更新组件。watchEffect 只接收一个参数,就是需要执行的回调函数。watchEffect的代码示例如下:

javascript 复制代码
const state = Vue.reactive({ count: 0 })
Vue.watchEffect(() => {
  console.log(`count变化了:${state.count}`);
})
state.count++ // 在控制台输出:'count变化了:1'

相比于 watchwatchEffect 有着更强大的自动侦测能力,并且可以省略对监听数据的声明,使用起来更加方便。但是需要注意的是,watchEffect中的回调函数应该是纯函数 ,不能直接修改响应式数据的值,否则会造成无限循环更新的危险。同时,watchEffect 也不支持监听特定的响应式数据,只能监听所有响应式数据的变化。

5. 如何使用 Vue3 中的 watchEffect 来实现响应式数据的监听和更新?有什么注意事项?

watchEffect 是 Vue3 中新增的一个响应式 API,用于监听和响应状态的变化。它的用法类似于 computed,但是它不会返回计算结果,而是直接执行函数并收集依赖,当依赖发生变化时,会重新执行函数。

使用 watchEffect 监听响应式数据的变化非常简单,只需要在一个函数中使用 reactiveref 定义响应式数据,并在函数中使用 watchEffect 监听数据的变化即可。例如:

js 复制代码
import { reactive, watchEffect } from 'vue'

const state = reactive({
  count: 0
})

watchEffect(() => {
  console.log(state.count)
})

上面的代码中,我们定义了一个响应式数据 state,然后使用 watchEffect 监听 state.count 的变化并输出变化后的值。当 state.count 的值发生变化时,watchEffect 会自动重新执行函数并输出最新的值。

注意事项:

  1. watchEffect 只能用在 setup 函数或单独的函数中,不能用在模板中。
  2. watchEffect 只能监听响应式数据的变化,不能监听非响应式数据的变化。
  3. watchEffect 返回的是一个停止监听的函数,可以在组件卸载时使用。
  4. watchEffect 中的依赖收集是自动的,不需要手动添加依赖,但是也要注意不要使用局部变量或闭包中的变量,因为它们不会被自动收集。

6. Vue3 中引入了 setup 方法,它有什么作用?它的执行时机是什么时候?

Vue3 中的 setup 方法是一个新的组件选项,用于代替 Vue2 中的 beforeCreatecreated 钩子函数以及 datamethods 等选项。它可以在组件实例创建之前执行,并且在组件实例创建之后,返回一个对象,将这个对象中的响应式数据以及函数暴露给组件模板使用。

以下是 setup 函数的简单示例:

javascript 复制代码
<template>
  <div>
    <p>{{ count }}</p>
    <button @click="increment">Increment</button>
  </div>
</template>

<script>
export default {
  setup() {
    const count = Vue.ref(0)

    const increment = () => {
      count.value++
    }

    return {
      count,
      increment
    }
  }
}
</script>

setup 函数中,首先定义了一个 count 变量和一个 increment 函数,通过 Vue.ref() 创建了一个响应式的 count,并将其暴露给组件模板中使用。同时,将 increment 函数也暴露给模板,当按钮被点击时,将会触发 increment 函数,修改 count 的值。

此外,setup 函数还可以接收 props 对象和 context 对象作为参数,这两个参数分别包含了组件的属性以及组件实例的上下文信息。

  • props 参数包含了通过组件标签传入的属性值,可以通过解构赋值的方式使用。

  • context 参数包含了一些常用的 Vue 实例方法和属性,比如 emit 用于触发父组件事件、attrs 用于获取非 prop 特性、slots 用于获取插槽等。

setup 函数的执行时机在组件实例创建之前,它会在 Vue 内部先进行一次 beforeCreate 钩子函数的调用,而在组件实例创建之后,它会在 created 钩子函数调用之前被执行。

  • 需要注意的是,只有在 setup 函数中返回的对象中包含的属性和方法才能在组件模板中使用。如果在 setup 函数之外定义属性和方法,就算在 setup 函数内部使用,也不能在模板中直接使用。

  • 总的来说,setup 函数为 Vue 3 中的组件开发带来了更好的灵活性和可维护性,让我们能够更加方便地编写代码,提高开发效率。

7. Vue3 中的 <template v-for>v-for 指令的区别和用法。

在Vue3中,<template v-for>v-for 指令都可以用来遍历数组或对象并生成多个元素。它们的主要区别在于语法和用法。

<template v-for>是一种特殊的语法,它允许我们在一个 <template> 标签内编写多个元素,然后使用 v-for 指令来循环渲染这些元素。例如:

html 复制代码
<template v-for="(item, index) in items">
  <li :key="index">{{ item }}</li>
</template>

在上面的例子中,<template>标签内包含了一个<li>元素,当v-for循环执行时,会根据items数组的长度生成多个<li>元素。使用<template v-for>的好处是可以避免在循环体内添加额外的标签,使得代码更简洁。

v-for指令的用法与Vue2相同。我们可以将v-for指令应用在任何元素上,例如:

html 复制代码
<ul>
  <li v-for="(item, index) in items" :key="index">{{ item }}</li>
</ul>

在上面的例子中,v-for指令被应用在<li>元素上,当循环执行时,会根据items数组的长度生成多个<li>元素。v-for指令的优点是可以应用在任何元素上,使得我们可以更灵活地控制循环生成的元素。

总的来说,<template v-for>v-for指令都可以用来循环生成多个元素,选择使用哪种方式取决于具体的需求和习惯。

小程序刷题

搜索: zerojs零技术

相关推荐
Jiaberrr15 分钟前
前端实战:使用JS和Canvas实现运算图形验证码(uniapp、微信小程序同样可用)
前端·javascript·vue.js·微信小程序·uni-app
LvManBa1 小时前
Vue学习记录之六(组件实战及BEM框架了解)
vue.js·学习·rust
200不是二百1 小时前
Vuex详解
前端·javascript·vue.js
LvManBa1 小时前
Vue学习记录之三(ref全家桶)
javascript·vue.js·学习
深情废杨杨2 小时前
前端vue-父传子
前端·javascript·vue.js
工业互联网专业2 小时前
毕业设计选题:基于springboot+vue+uniapp的驾校报名小程序
vue.js·spring boot·小程序·uni-app·毕业设计·源码·课程设计
J不A秃V头A3 小时前
Vue3:编写一个插件(进阶)
前端·vue.js
司篂篂3 小时前
axios二次封装
前端·javascript·vue.js
姚*鸿的博客3 小时前
pinia在vue3中的使用
前端·javascript·vue.js
天下无贼!5 小时前
2024年最新版Vue3学习笔记
前端·vue.js·笔记·学习·vue