前端八股Vue---Vue2和Vue3的区别,set up的用法

目录

一、核心区别速览

二、详细对比

[1. 响应式原理不同(最重要)](#1. 响应式原理不同(最重要))

[2. 写法不同(最明显)](#2. 写法不同(最明显))

[3. 生命周期变化](#3. 生命周期变化)

[4. 性能提升](#4. 性能提升)

[5. 其他重要区别](#5. 其他重要区别)

[5.1 多根节点(Fragment)](#5.1 多根节点(Fragment))

[5.2 Teleport(传送门)](#5.2 Teleport(传送门))

[5.3 Suspense(异步组件)](#5.3 Suspense(异步组件))

[5.4 根实例创建方式](#5.4 根实例创建方式)

[5.5 移除的 API](#5.5 移除的 API)

[三、setup 提供的核心优势](#三、setup 提供的核心优势)

[四、setup 怎么用?](#四、setup 怎么用?)

[4.1 传统写法(setup 函数)](#4.1 传统写法(setup 函数))

[4.2 现代写法script setup语法糖](#4.2 现代写法script setup语法糖)

[4.3 script setup的优势](#4.3 script setup的优势)

五、面试高频问题

[Q1:Vue2 和 Vue3 的区别有哪些?](#Q1:Vue2 和 Vue3 的区别有哪些?)

[Q2:setup 提供了什么?](#Q2:setup 提供了什么?)

[Q3:script setup和普通 script有什么区别?](#Q3:script setup和普通 script有什么区别?)


一、核心区别速览

对比维度 Vue2 Vue3
响应式原理 Object.defineProperty Proxy
API 风格 Options API(选项式) Composition API(组合式)
生命周期 beforeCreate、created... setup 代替前两个,其他加 on
性能 一般 更快、更小
TypeScript 支持较弱 原生支持
根实例创建 new Vue() createApp()
多根节点 ❌ 不支持 ✅ 支持(Fragment)
Teleport ❌ 无 ✅ 有
Suspense ❌ 无 ✅ 有

二、详细对比

1. 响应式原理不同(最重要)

Vue2:Object.defineProperty

javascript 复制代码
// Vue2 响应式原理(简化)
Object.defineProperty(obj, 'name', {
  get() { /* 收集依赖 */ },
  set() { /* 触发更新 */ }
})

// 问题1:新增属性监听不到
this.user.newProp = 'hello'  // ❌ 不响应,需要 $set
this.$set(this.user, 'newProp', 'hello')  // ✅ 需要额外 API

// 问题2:删除属性监听不到
delete this.user.name  // ❌ 不响应,需要 $delete

// 问题3:数组下标修改监听不到
this.list[0] = newValue  // ❌ 不响应

Vue3:Proxy

javascript 复制代码
// Vue3 响应式原理(简化)
const proxy = new Proxy(obj, {
  get(target, key) { /* 收集依赖 */ },
  set(target, key, value) { /* 触发更新 */ },
  deleteProperty(target, key) { /* 触发更新 */ }
})

// ✅ 新增属性自动响应
state.user.newProp = 'hello'  // ✅ 自动响应

// ✅ 删除属性自动响应
delete state.user.name  // ✅ 自动响应

// ✅ 数组下标自动响应
state.list[0] = newValue  // ✅ 自动响应

// 不需要 $set、$delete

2. 写法不同(最明显)

Vue2:Options API

javascript 复制代码
<script>
export default {
  data() {
    return {
      count: 0,
      user: null
    }
  },
  computed: {
    double() {
      return this.count * 2
    }
  },
  methods: {
    increment() {
      this.count++
    }
  },
  mounted() {
    this.fetchUser()
  }
}
</script>

Vue3:Composition API

javascript 复制代码
<script setup>
import { ref, computed, onMounted } from 'vue'

// 计数器逻辑(聚在一起)
const count = ref(0)
const double = computed(() => count.value * 2)
const increment = () => count.value++

// 用户逻辑(聚在一起)
const user = ref(null)
const fetchUser = async () => {
  user.value = await api.getUser()
}
onMounted(() => {
  fetchUser()
})
</script>

3. 生命周期变化

Vue2 Vue3 (Options API) Vue3 (Composition API)
beforeCreate beforeCreate ❌ 不需要(setup 替代)
created created ❌ 不需要(setup 替代)
beforeMount beforeMount onBeforeMount
mounted mounted onMounted
beforeUpdate beforeUpdate onBeforeUpdate
updated updated onUpdated
beforeDestroy beforeUnmount onBeforeUnmount
destroyed unmounted onUnmounted

4. 性能提升

优化点 说明
Tree shaking 未使用的代码不打包,体积更小
Diff 算法优化 增加静态标记,只对比动态内容
静态节点提升 静态节点只创建一次,复用
事件缓存 事件处理函数缓存,减少内存开销

5. 其他重要区别

5.1 多根节点(Fragment)
javascript 复制代码
<!-- Vue2:必须只有一个根节点 -->
<template>
  <div>  <!-- 必须有一个包裹元素 -->
    <h1>标题</h1>
    <p>内容</p>
  </div>
</template>

<!-- Vue3:支持多个根节点 -->
<template>
  <h1>标题</h1>
  <p>内容</p>
</template>
5.2 Teleport(传送门)
javascript 复制代码
<!-- 弹窗挂载到 body,避免被父组件样式影响 -->
<template>
  <teleport to="body">
    <div class="modal">
      <h3>弹窗标题</h3>
      <p>弹窗内容</p>
    </div>
  </teleport>
</template>
5.3 Suspense(异步组件)
javascript 复制代码
<template>
  <Suspense>
    <template #default>
      <AsyncComponent />  <!-- 异步组件 -->
    </template>
    <template #fallback>
      <div>加载中...</div>  <!-- 加载时显示 -->
    </template>
  </Suspense>
</template>
5.4 根实例创建方式
javascript 复制代码
// Vue2
import Vue from 'vue'
import App from './App.vue'

const vm = new Vue({
  render: h => h(App)
}).$mount('#app')

// Vue3
import { createApp } from 'vue'
import App from './App.vue'

const app = createApp(App)
app.mount('#app')
5.5 移除的 API
移除项 替代方案
$on$off mitt、事件总线
$set$delete 不需要了(Proxy 自动响应)
过滤器 计算属性或方法
$children 使用 $refs

三、setup 提供的核心优势

优势 说明
按功能组织代码 相关逻辑放在一起,而不是分散在 data、methods、mounted
逻辑复用 可以封装成自定义 Hooks,在多个组件间复用
TypeScript 友好 类型推导完美,不需要额外类型声明
更好的性能 编译时优化,减少运行时开销
没有 this 困扰 普通函数中用变量,不用担心 this 指向
Tree-shaking 支持 未使用的 API 不会打包

四、setup 怎么用?

4.1 传统写法(setup 函数)

javascript 复制代码
<script>
import { ref } from 'vue'

export default {
  setup() {
    const count = ref(0)
    const increment = () => count.value++
    
    // 必须 return,才能在模板中使用
    return { count, increment }
  }
}
</script>

4.2 现代写法script setup语法糖

<script setup> 语法糖)

javascript 复制代码
<script setup>
import { ref } from 'vue'

// 直接写,不需要 return
const count = ref(0)
const increment = () => count.value++
</script>

<template>
  <button @click="increment">{{ count }}</button>
</template>

4.3 script setup的优势

优势 说明
代码更少 不需要 export defaultreturn
自动暴露 定义的变量、函数自动在模板可用
更好的性能 编译时优化
更好的 TS 支持 类型推导更准确

五、面试高频问题

Q1:Vue2 和 Vue3 的区别有哪些?

答:

  1. 响应式原理 :Vue2 用 Object.defineProperty,Vue3 用 Proxy(能监听新增、删除、数组)

  2. API 风格 :Vue2 是 Options API,Vue3 是 Composition API(<script setup>

  3. 生命周期 :Vue3 用 setup 代替 beforeCreate/created,其他加 on 前缀

  4. 性能:Vue3 打包更小、渲染更快

  5. 新特性:Vue3 支持多根节点、Teleport、Suspense

  6. TypeScript:Vue3 原生支持更好

  7. 根实例 :Vue2 用 new Vue(),Vue3 用 createApp()

Q2:setup 提供了什么?

答:setup 是 Vue3 组合式 API 的入口,提供了以下核心能力:

  1. 响应式 APIrefreactive

  2. 计算属性computed

  3. 侦听器watchwatchEffect

  4. 生命周期onMountedonUpdatedonUnmounted

  5. 组件通信definePropsdefineEmitsdefineExpose

  6. 依赖注入provideinject

  7. 模板引用ref

核心优势:代码按功能组织、逻辑复用方便、TypeScript 友好、没有 this 困扰、性能更好。

Q3: script setup和普通 script有什么区别?

答:

  • <script setup> 是语法糖,代码更简洁,不需要 return

  • 定义的变量、函数自动在模板中可用

  • 更好的性能(编译时优化)和 TypeScript 支持

  • 是 Vue 3 推荐写法

相关推荐
weixin_BYSJ19879 分钟前
SpringBoot + MySQL 乒乓球运动员信息管理系统项目实战--附源码04954
java·javascript·spring boot·python·django·flask·php
沪飘大军1 小时前
ll-llm:一个零依赖、可插拔的 OpenAI 兼容 LLM 代理
javascript
leoZ2311 小时前
Claude 驱动的全栈开发:Spring Boot + Vue 的 BS 架构实践
vue.js·spring boot·架构
kyriewen2 小时前
我扒了 GPT-5.6 的全部编程跑分——有一项 OpenAI 没敢放出来
前端·gpt·ai编程
前端H2 小时前
微前端 v3 架构升级:从加载隔离到状态协同
前端·架构·状态模式
山河木马2 小时前
GPU自动处理专题3-NDC怎么映射成屏幕像素坐标(视口变换)
javascript·webgl·图形学
陆枫Larry3 小时前
小程序包体积优化:用 SVG 图片替换 iconfont,并保留 CSS 控色能力
前端
Appthing4 小时前
在 TanStack Start 中使用 VitePWA 的正确配置
javascript
环境栈笔记5 小时前
多账号浏览器选型检查清单:Profile、权限、Session 和任务日志怎么评估
前端·人工智能·后端·自动化
前端炒粉5 小时前
手写promise
java·前端·javascript