Vue2 & Vue3 面试题大全(超详细版)
目录
- Vue 基础概念
- Vue2 核心原理
- Vue3 核心原理
- 响应式原理
- 生命周期
- 组件通信
- 路由相关
- Vuex / Pinia
- Composition API
- 性能优化
- 虚拟 DOM
- Diff 算法
- nextTick
- SSR
- TypeScript
- 工程化
- 权限系统
- 项目实战
- 高频场景题
- Vue2 和 Vue3 区别
- Vue 面试场景题
- Vue 项目优化
- Vue 常见报错
- Vue 面试总结
一、Vue 基础概念面试题
1. 什么是 Vue?
答案
Vue 是一个渐进式 JavaScript 前端框架,主要用于构建用户界面。
核心特点:
- 数据驱动
- 组件化开发
- 虚拟 DOM
- 响应式系统
- 单页面应用(SPA)支持
- 生态完善
Vue 的核心思想:
text
数据驱动视图
也就是:
text
数据变化 → 页面自动更新
2. 什么是 MVVM?
答案
MVVM:
text
Model
View
ViewModel
各部分含义
| 名称 | 作用 |
|---|---|
| Model | 数据层 |
| View | 视图层 |
| ViewModel | Vue实例,负责连接数据和视图 |
Vue 的核心:
js
const vm = new Vue({
data() {
return {
msg: 'hello'
}
}
})
vm 就是 ViewModel。
3. Vue 的特点有哪些?
答案
1)响应式
数据变化自动更新页面。
2)组件化
页面拆分成多个组件。
3)虚拟 DOM
提高渲染性能。
4)渐进式
可以逐步使用。
5)生态完善
包括:
- Vue Router
- Vuex
- Pinia
- Vite
- Nuxt
二、Vue2 和 Vue3 区别(超级高频)
1. Vue2 和 Vue3 最大区别是什么?
答案
| Vue2 | Vue3 |
|---|---|
| Object.defineProperty | Proxy |
| Options API | Composition API |
| 性能一般 | 性能更强 |
| 不支持 Tree Shaking | 支持 |
| TS 支持差 | TS 支持更好 |
| 生命周期不同 | 生命周期更统一 |
| Vuex | Pinia 更推荐 |
2. Vue3 为什么使用 Proxy?
答案
Vue2 使用:
js
Object.defineProperty
缺点:
- 无法监听数组变化
- 无法监听对象新增属性
- 性能较差
Vue3 使用:
js
Proxy
优势:
- 监听整个对象
- 支持数组
- 支持 Map/Set
- 性能更好
- 拦截更多操作
示例:
js
const obj = {
name: '张三'
}
const proxy = new Proxy(obj, {
get(target, key) {
return target[key]
},
set(target, key, value) {
target[key] = value
return true
}
})
3. 什么是 Composition API?
答案
Vue3 推出的组合式 API。
Vue2:
js
export default {
data() {},
methods: {},
computed: {}
}
Vue3:
js
setup() {}
优点:
- 逻辑复用更强
- 代码更清晰
- TypeScript 更友好
- 大项目更容易维护
示例:
js
import { ref } from 'vue'
export default {
setup() {
const count = ref(0)
const add = () => {
count.value++
}
return {
count,
add
}
}
}
三、Vue 生命周期面试题
1. Vue 生命周期有哪些?
Vue2 生命周期
| 生命周期 | 说明 |
|---|---|
| beforeCreate | 实例创建前 |
| created | 实例创建完成 |
| beforeMount | 挂载前 |
| mounted | 挂载完成 |
| beforeUpdate | 更新前 |
| updated | 更新后 |
| beforeDestroy | 销毁前 |
| destroyed | 销毁后 |
2. Vue3 生命周期有哪些变化?
答案
Vue3:
| Vue2 | Vue3 |
|---|---|
| beforeDestroy | beforeUnmount |
| destroyed | unmounted |
Vue3 使用:
js
import {
onMounted,
onUnmounted
} from 'vue'
3. created 和 mounted 区别?
答案
created
- 数据已经初始化
- DOM 还没生成
mounted
- DOM 已生成
- 可以操作 DOM
例如:
js
mounted() {
console.log(this.$refs.box)
}
4. 一般在哪个生命周期发送请求?
答案
通常:
text
created
或者
mounted
Vue3:
js
onMounted(() => {
getList()
})
原因:
- 数据已初始化
- 页面开始渲染
四、Vue 响应式原理
1. Vue2 响应式原理
答案
Vue2 使用:
js
Object.defineProperty
核心流程:
text
数据劫持
→ getter 收集依赖
→ setter 派发更新
源码思想:
js
Object.defineProperty(obj, 'name', {
get() {
return value
},
set(newVal) {
value = newVal
update()
}
})
2. Vue3 响应式原理
答案
Vue3 使用:
js
Proxy + Reflect
示例:
js
const obj = reactive({
name: 'Vue3'
})
内部:
js
new Proxy()
优势:
- 深层监听
- 动态属性
- 数组监听
- 性能更强
3. ref 和 reactive 区别?
答案
| ref | reactive |
|---|---|
| 基本类型 | 对象类型 |
| 使用 .value | 不需要 |
| 底层 reactive | Proxy |
ref
js
const count = ref(0)
count.value++
reactive
js
const user = reactive({
name: '张三'
})
4. watch 和 computed 区别?
答案
| computed | watch |
|---|---|
| 有缓存 | 无缓存 |
| 计算属性 | 监听变化 |
| 返回值 | 执行逻辑 |
computed
js
const total = computed(() => {
return price.value * num.value
})
watch
js
watch(count, (newVal) => {
console.log(newVal)
})
五、nextTick 面试题
1. 什么是 nextTick?
答案
Vue 是异步更新 DOM。
nextTick:
text
等待 DOM 更新完成后执行
示例:
js
this.msg = 'hello'
this.$nextTick(() => {
console.log(this.$refs.box)
})
Vue3:
js
import { nextTick } from 'vue'
2. nextTick 原理是什么?
答案
内部使用:
- Promise
- MutationObserver
- setTimeout
优先使用微任务。
六、组件通信面试题
1. 父传子怎么实现?
答案
使用:
text
props
父组件:
html
<Child :msg="msg" />
子组件:
js
props: {
msg: String
}
2. 子传父怎么实现?
答案
使用:
text
$emit
子组件:
js
this.$emit('send', data)
父组件:
html
<Child @send="getData" />
3. 兄弟组件通信怎么实现?
答案
方法:
- EventBus(Vue2)
- Vuex
- Pinia
- mitt(Vue3)
mitt:
js
import mitt from 'mitt'
const emitter = mitt()
4. provide 和 inject 是什么?
答案
跨层级组件通信。
父组件:
js
provide('name', 'Vue3')
子组件:
js
const name = inject('name')
七、v-if 和 v-show 区别
答案
| v-if | v-show |
|---|---|
| 真正销毁 DOM | display:none |
| 切换慢 | 切换快 |
| 初始渲染慢 | 初始渲染快 |
| 高频切换不适合 | 高频切换适合 |
八、v-for 和 key 面试题
1. 为什么 v-for 要加 key?
答案
key 用于:
text
提高 diff 算法效率
避免 DOM 错乱。
错误:
html
<li v-for="item in list" :key="index">
推荐:
html
<li v-for="item in list" :key="item.id">
2. 为什么不推荐 index 作为 key?
答案
因为:
text
数组顺序变化会导致复用错误
例如:
- 输入框错乱
- DOM 复用异常
九、虚拟 DOM 面试题
1. 什么是虚拟 DOM?
答案
虚拟 DOM:
text
使用 JS 对象描述真实 DOM
示例:
js
{
tag: 'div',
children: []
}
优势:
- 减少真实 DOM 操作
- 提高性能
- 跨平台
2. Diff 算法是什么?
答案
Vue 会对比新旧虚拟 DOM。
找到变化部分。
只更新变化区域。
核心优化:
- 同层比较
- key 优化
- 双端比较
十、Vue Router 面试题
1. hash 和 history 区别?
答案
| hash | history |
|---|---|
| 有 # | 无 # |
| 不需要后端配置 | 需要后端支持 |
| SEO 差 | SEO 好 |
Vue3:
js
createWebHistory()
js
createWebHashHistory()
2. 路由守卫有哪些?
答案
全局守卫
js
router.beforeEach()
路由独享守卫
js
beforeEnter
组件守卫
js
beforeRouteEnter
3. 路由懒加载怎么实现?
答案
js
const Home = () => import('@/views/Home.vue')
作用:
- 减少首屏加载
- 提高性能
十一、Vuex 和 Pinia 面试题
1. Vuex 核心概念有哪些?
答案
| 名称 | 作用 |
|---|---|
| state | 数据 |
| getters | 计算属性 |
| mutations | 同步修改 |
| actions | 异步操作 |
| modules | 模块化 |
2. 为什么 mutations 必须同步?
答案
因为 Vue DevTools 需要追踪状态变化。
异步会导致状态不可追踪。
3. Pinia 和 Vuex 区别?
答案
| Pinia | Vuex |
|---|---|
| 更简单 | 较复杂 |
| TS 更好 | TS 一般 |
| 无 mutations | 有 mutations |
| 支持 Composition API | Vue2 风格 |
示例:
js
export const useUserStore = defineStore('user', {
state: () => ({
name: 'Vue3'
})
})
十二、Vue 性能优化面试题
1. Vue 项目怎么优化?
答案
代码层面
- v-show 替代 v-if
- key 优化
- computed 缓存
- 路由懒加载
- 图片懒加载
- keep-alive
工程层面
- gzip
- CDN
- Tree Shaking
- 分包
- Vite
用户体验
- 骨架屏
- SSR
- 缓存
2. keep-alive 是什么?
答案
缓存组件。
避免重复渲染。
html
<keep-alive>
<router-view />
</keep-alive>
生命周期:
- activated
- deactivated
十三、Vue3 setup 面试题
1. setup 执行时机?
答案
在:
text
beforeCreate 前
执行。
setup 中:
text
没有 this
2. script setup 是什么?
答案
Vue3 语法糖。
vue
<script setup>
import { ref } from 'vue'
const count = ref(0)
</script>
优点:
- 更简洁
- 性能更好
- 更适合 TS
十四、Vue 常见场景题
1. 页面白屏怎么排查?
答案
排查:
- 控制台报错
- 路由问题
- API 请求失败
- 静态资源 404
- 打包路径错误
- nginx 配置错误
2. 首屏加载慢怎么优化?
答案
优化:
- 路由懒加载
- CDN
- gzip
- 图片压缩
- Tree Shaking
- SSR
- Vite
- HTTP缓存
3. 大列表卡顿怎么优化?
答案
方案:
- 虚拟列表
- 分页
- 防抖节流
- Web Worker
- 懒加载
常见库:
- vue-virtual-scroll-list
十五、Vue 高频面试题(简答版)
1. 为什么 data 是函数?
避免组件数据共享。
2. Vue 为什么不能检测数组下标变化?(Vue2)
因为 Object.defineProperty 无法监听数组索引。
3. Vue2 如何解决数组更新?
重写数组方法:
- push
- pop
- shift
- splice
4. 为什么不建议直接操作 DOM?
会破坏 Vue 数据驱动。
5. computed 为什么有缓存?
依赖不变不会重新计算。
6. watch 深度监听怎么实现?
js
watch: {
obj: {
handler() {},
deep: true
}
}
7. Vue3 为什么更快?
- Proxy
- 编译优化
- 静态提升
- PatchFlag
- Tree Shaking
十六、Vue 项目实战面试题
1. 权限系统怎么做?
答案
一般:
- 登录
- token
- 动态路由
- 按钮权限
- 菜单权限
技术:
- Vue Router
- Pinia/Vuex
- axios 拦截器
2. axios 二次封装怎么做?
答案
封装:
- baseURL
- 请求拦截
- 响应拦截
- token
- 错误处理
示例:
js
service.interceptors.request.use(config => {
return config
})
3. 如何封装组件?
答案
思路:
- props
- emit
- 插槽
- 暴露方法
- 样式隔离
十七、TypeScript + Vue 面试题
1. Vue3 为什么更适合 TypeScript?
答案
因为:
- Composition API 类型推导更强
- setup 更清晰
- Proxy 更容易推导
2. defineProps 是什么?
答案
vue
<script setup lang="ts">
interface Props {
title: string
}
defineProps<Props>()
</script>
十八、Vue 面试项目回答模板
1. 项目介绍怎么回答?
模板
text
项目主要使用 Vue3 + Vite + TypeScript + Pinia 开发。
负责:
- 页面开发
- 组件封装
- 权限系统
- 接口联调
- 性能优化
优化:
- 路由懒加载
- keep-alive
- 图片压缩
- Echarts 按需引入
2. 遇到过什么难点?
模板
text
大数据表格卡顿。
解决:
- 虚拟列表
- 分页
- 防抖
- keep-alive
十九、Vue 面试加分项
高级方向
1)源码
- 响应式原理
- Diff 算法
- patch
- effect
- dep
2)工程化
- webpack
- vite
- CI/CD
- Docker
3)性能优化
- SSR
- 微前端
- CDN
- 分包
4)架构能力
- 低代码
- 组件库
- 中后台
- 可视化大屏
二十、Vue 面试终极总结
Vue2 必会
- 生命周期
- 组件通信
- Vuex
- nextTick
- Diff
- v-if 和 v-show
- watch/computed
Vue3 必会
- setup
- ref/reactive
- Composition API
- Pinia
- script setup
- hooks 封装
- TS
高频项目题
- 权限系统
- 性能优化
- 封装组件
- axios 封装
- 路由守卫
- 大屏项目
- Echarts
二十一、Vue 官方文档与学习资源
Vue 官方
- Vue2 官方:https://v2.cn.vuejs.org/
- Vue3 官方:https://cn.vuejs.org/
Router
- Vue Router:https://router.vuejs.org/zh/
Pinia
Vite
TypeScript
UI 框架
- Element Plus:https://element-plus.org/
- Ant Design Vue:https://www.antdv.com/
- Naive UI:https://www.naiveui.com/
二十二、Vue 面试建议
初级
重点:
- 生命周期
- 组件通信
- Vue Router
- Vuex
- 基础语法
中级
重点:
- Vue3
- Pinia
- Composition API
- 权限系统
- 性能优化
高级
重点:
- Vue源码
- Diff算法
- SSR
- 微前端
- 工程化
- 架构设计
结束语
如果你能掌握:
- Vue2 核心原理
- Vue3 核心原理
- 项目实战
- 性能优化
- 工程化
- TypeScript
基本已经具备:
text
中高级前端工程师能力
建议:
- 多做项目
- 多看源码
- 多总结面试题
- 多刷真实业务场景
加油。