Vue3 完整学习路径指南

释放双眼,带上耳机,听听看~!
Vue3 Logo

目录

  1. Vue3 基础语法
  2. 组合式 API
  3. Vue Router
  4. Pinia 状态管理
  5. TypeScript 集成
  6. 实战项目
  7. 学习资源推荐

Vue3 基础语法

Vue3 的模板语法是基于 HTML 的声明式语法,它允许我们在 HTML 中嵌入 Vue 的特殊标记,将响应式数据与 DOM 绑定。

Vue3模板语法

1.1 插值表达式

文本插值:最基础的数据绑定方式

<template>  <div>    <!-- 文本插值 -->    <h1>{{ message }}</h1>    <!-- 表达式支持 -->    <p>{{ count + 1 }}</p>    <p>{{ isActive ? 'Active' : 'Inactive' }}</p>    <!-- 原始HTML -->    <div v-html="rawHtml"></div>  </div></template><script setup>import { ref } from 'vue'const message = ref('Hello Vue3!')const count = ref(0)const isActive = ref(true)const rawHtml = ref('<strong>这是加粗的文本</strong>')</script>

1.2 指令系统

Vue 提供了丰富的指令来处理各种 DOM 操作:

v-bind:属性绑定

<template>  <!-- 完整语法 -->  <img v-bind:src="imageUrl" v-bind:alt="imageAlt">  <!-- 缩写语法 -->  <img :src="imageUrl" :alt="imageAlt">  <!-- 动态属性名 -->  <div :[dynamicAttr]="value"></div></template>

v-if/v-else:条件渲染

<template>  <div v-if="isLoggedIn">    <p>欢迎回来,{{ username }}</p>  </div>  <div v-else>    <p>请登录</p>  </div></template>

v-for:列表渲染

<template>  <ul>    <li v-for="(item, index) in items" :key="item.id">      {{ index }} - {{ item.name }}    </li>  </ul></template><script setup>import { ref } from 'vue'const items = ref([  { id: 1, name: '苹果' },  { id: 2, name: '香蕉' },  { id: 3, name: '橙子' }])</script>

v-on:事件处理

<template>  <!-- 完整语法 -->  <button v-on:click="handleClick">点击我</button>  <!-- 缩写语法 -->  <button @click="handleClick">点击我</button>  <!-- 事件修饰符 -->  <form @submit.prevent="handleSubmit">    <input @keyup.enter="handleEnter">  </form></template><script setup>const handleClick = () => {  console.log('按钮被点击了')}const handleSubmit = (event) => {  console.log('表单提交', event)}const handleEnter = () => {  console.log('按下了Enter键')}</script>

v-model:双向绑定

<template>  <!-- 文本输入 -->  <input v-model="message" placeholder="输入文本">  <!-- 复选框 -->  <input type="checkbox" v-model="isChecked">  <!-- 单选按钮 -->  <input type="radio" v-model="selected" value="option1">  <!-- 选择框 -->  <select v-model="selectedOption">    <option value="option1">选项1</option>    <option value="option2">选项2</option>  </select></template><script setup>import { ref } from 'vue'const message = ref('')const isChecked = ref(false)const selected = ref('option1')const selectedOption = ref('option1')</script>

1.3 响应式数据

Vue3 提供了两种创建响应式数据的方式:

ref:用于基本类型数据

<script setup>import { ref } from 'vue'// 创建响应式基本类型const count = ref(0)const message = ref('Hello')const isActive = ref(true)// 修改值需要使用.valueconst increment = () => {  count.value++}</script>

reactive:用于对象类型数据

<script setup>import { reactive } from 'vue'// 创建响应式对象const state = reactive({  count: 0,  user: {    name: '张三',    age: 25  }})// 直接修改属性const updateUser = () => {  state.user.name = '李四'  state.count++}</script>

toRefs:将 reactive 对象转换为 ref 对象

<script setup>import { reactive, toRefs } from 'vue'const state = reactive({  count: 0,  message: 'Hello'})// 将reactive对象转换为ref对象const { count, message } = toRefs(state)</script>

组合式 API

组合式 API 是 Vue3 的核心特性,它允许我们将组件逻辑按功能关注点组织,而不是按选项类型组织。

Vue3组合式API

2.1 setup 函数

setup 是组合式 API 的入口点,在组件创建时执行:

<template>  <div>    <h1>{{ message }}</h1>    <p>Count: {{ count }}</p>    <button @click="increment">增加</button>  </div></template><script setup>import { ref } from 'vue'// setup函数在组件创建时执行const message = ref('Hello Composition API!')const count = ref(0)const increment = () => {  count.value++}</script>

2.2 计算属性

使用 computed 创建计算属性:

<script setup>import { ref, computed } from 'vue'const firstName = ref('张')const lastName = ref('三')// 计算属性const fullName = computed(() => {  return `${firstName.value}${lastName.value}`})// 可写计算属性const fullName2 = computed({  get() {    return `${firstName.value}${lastName.value}`  },  set(value) {    const [first, last] = value.split(' ')    firstName.value = first    lastName.value = last  }})</script>

2.3 监听器

使用 watch 监听数据变化:

<script setup>import { ref, watch } from 'vue'const count = ref(0)const message = ref('Hello')// 监听单个数据源watch(count, (newValue, oldValue) => {  console.log(`count从${oldValue}变为${newValue}`)})// 监听多个数据源watch([count, message], ([newCount, newMessage], [oldCount, oldMessage]) => {  console.log('数据发生变化')})// 监听对象属性const state = ref({  count: 0,  message: 'Hello'})watch(() => state.value.count, (newValue) => {  console.log(`count变为${newValue}`)})// 深度监听watch(state, (newValue) => {  console.log('state发生变化', newValue)}, { deep: true })</script>

2.4 生命周期钩子

在组合式 API 中使用生命周期钩子:

<script setup>import {   onMounted,   onUpdated,   onUnmounted,  onBeforeMount,  onBeforeUpdate,  onBeforeUnmount} from 'vue'// 组件挂载后onMounted(() => {  console.log('组件已挂载')})// 组件更新后onUpdated(() => {  console.log('组件已更新')})// 组件卸载前onBeforeUnmount(() => {  console.log('组件即将卸载')})// 组件卸载后onUnmounted(() => {  console.log('组件已卸载')})</script>

2.5 自定义 Hook

将可复用逻辑封装为自定义 Hook:

// hooks/useCounter.jsimport { ref, computed } from 'vue'export function useCounter(initialValue = 0) {  const count = ref(initialValue)  const increment = () => {    count.value++  }  const decrement = () => {    count.value--  }  const reset = () => {    count.value = initialValue  }  const doubleCount = computed(() => count.value * 2)  return {    count,    doubleCount,    increment,    decrement,    reset  }}

使用自定义 Hook:

<template>  <div>    <p>Count: {{ count }}</p>    <p>Double: {{ doubleCount }}</p>    <button @click="increment">+</button>    <button @click="decrement">-</button>    <button @click="reset">Reset</button>  </div></template><script setup>import { useCounter } from '@/hooks/useCounter'const { count, doubleCount, increment, decrement, reset } = useCounter(0)</script>

Vue Router

Vue Router 是 Vue 官方的路由管理器,用于构建单页应用。

Vue Router

3.1 安装和配置

首先安装 Vue Router:

npm install vue-router@4

创建路由配置文件:

// router/index.jsimport { createRouter, createWebHistory } from 'vue-router'import HomeView from '../views/HomeView.vue'import AboutView from '../views/AboutView.vue'import UserView from '../views/UserView.vue'import NotFoundView from '../views/NotFoundView.vue'const routes = [  {    path: '/',    name: 'home',    component: HomeView  },  {    path: '/about',    name: 'about',    component: AboutView  },  {    path: '/user/:id',    name: 'user',    component: UserView,    props: true // 将路由参数作为props传递  },  {    path: '/:pathMatch(.*)*',    name: 'not-found',    component: NotFoundView  }]const router = createRouter({  history: createWebHistory(import.meta.env.BASE_URL),  routes})export default router

在 main.js 中使用路由:

// main.jsimport { createApp } from 'vue'import App from './App.vue'import router from './router'createApp(App)  .use(router)  .mount('#app')

3.2 路由组件

在 App.vue 中添加路由出口:

<template>  <div id="app">    <nav>      <RouterLink to="/">首页</RouterLink> |      <RouterLink to="/about">关于</RouterLink> |      <RouterLink :to="{ name: 'user', params: { id: 1 } }">用户1</RouterLink>    </nav>    <!-- 路由出口 -->    <RouterView />  </div></template><script setup>import { RouterLink, RouterView } from 'vue-router'</script>

3.3 路由参数和查询

获取路由参数:

<template>  <div>    <h1>用户详情</h1>    <p>用户ID: {{ userId }}</p>    <p>查询参数: {{ query }}</p>  </div></template><script setup>import { useRoute } from 'vue-router'const route = useRoute()// 获取路由参数const userId = route.params.id// 获取查询参数const query = route.query</script>

3.4 编程式导航

使用编程方式进行导航:

<template>  <div>    <button @click="goToHome">返回首页</button>    <button @click="goToUser(2)">查看用户2</button>    <button @click="goBack">返回</button>  </div></template><script setup>import { useRouter } from 'vue-router'const router = useRouter()const goToHome = () => {  router.push('/')}const goToUser = (id) => {  router.push({    name: 'user',    params: { id },    query: { tab: 'profile' }  })}const goBack = () => {  router.go(-1)}</script>

3.5 路由守卫

使用路由守卫控制页面访问:

// router/index.jsrouter.beforeEach((to, from, next) => {  // 检查是否需要登录  const requiresAuth = to.matched.some(record => record.meta.requiresAuth)  const isLoggedIn = localStorage.getItem('token')  if (requiresAuth && !isLoggedIn) {    next('/login')  } else {    next()  }})// 添加需要登录的路由const routes = [  {    path: '/dashboard',    component: DashboardView,    meta: { requiresAuth: true }  }]

Pinia 状态管理

Pinia 是 Vue 官方推荐的状态管理库,替代了 Vuex。

Pinia状态管理

4.1 安装和配置

首先安装 Pinia:

npm install pinia

创建 Pinia 实例:

// main.jsimport { createApp } from 'vue'import { createPinia } from 'pinia'import App from './App.vue'const app = createApp(App)const pinia = createPinia()app.use(pinia)app.mount('#app')

4.2 创建 Store

使用 defineStore 创建 Store:

// stores/counter.jsimport { defineStore } from 'pinia'export const useCounterStore = defineStore('counter', {  // 状态  state: () => ({    count: 0,    name: 'Vue3'  }),  // 计算属性  getters: {    doubleCount: (state) => state.count * 2,    greeting: (state) => `Hello ${state.name}!`  },  // 方法  actions: {    increment() {      this.count++    },    decrement() {      this.count--    },    reset() {      this.count = 0    },    setName(newName) {      this.name = newName    }  }})

4.3 使用 Store

在组件中使用 Store:

<template>  <div>    <h1>{{ counterStore.greeting }}</h1>    <p>Count: {{ counterStore.count }}</p>    <p>Double Count: {{ counterStore.doubleCount }}</p>    <button @click="counterStore.increment">+</button>    <button @click="counterStore.decrement">-</button>    <button @click="counterStore.reset">Reset</button>    <input v-model="newName" @keyup.enter="updateName">  </div></template><script setup>import { useCounterStore } from '@/stores/counter'import { ref } from 'vue'// 获取Store实例const counterStore = useCounterStore()const newName = ref('')const updateName = () => {  if (newName.value) {    counterStore.setName(newName.value)    newName.value = ''  }}</script>

4.4 修改状态的方法

有多种方式可以修改 Store 状态:

<script setup>import { useCounterStore } from '@/stores/counter'const counterStore = useCounterStore()// 1. 直接修改counterStore.count++// 2. 使用actioncounterStore.increment()// 3. 使用$patch修改多个属性counterStore.$patch({  count: counterStore.count + 1,  name: 'Vue3 Updated'})// 4. 使用$patch函数counterStore.$patch((state) => {  state.count++  state.name = 'Vue3 Updated'})// 5. 替换整个状态counterStore.$state = {  count: 10,  name: 'Vue3 Reset'}</script>

4.5 监听 Store 变化

监听 Store 状态变化:

<script setup>import { useCounterStore } from '@/stores/counter'import { watch } from 'vue'const counterStore = useCounterStore()// 监听整个Storewatch(  counterStore,  (state) => {    console.log('Store状态变化:', state)  },  { deep: true })// 监听特定属性watch(  () => counterStore.count,  (newValue, oldValue) => {    console.log(`count从${oldValue}变为${newValue}`)  })// 使用$subscribe监听counterStore.$subscribe((mutation, state) => {  console.log('Mutation:', mutation)  console.log('New state:', state)})</script>

4.6 Store 组合

组合多个 Store:

// stores/user.jsimport { defineStore } from 'pinia'export const useUserStore = defineStore('user', {  state: () => ({    user: null,    isLoggedIn: false  }),  actions: {    login(userData) {      this.user = userData      this.isLoggedIn = true      localStorage.setItem('token', userData.token)    },    logout() {      this.user = null      this.isLoggedIn = false      localStorage.removeItem('token')    }  }})

在另一个 Store 中使用:

// stores/cart.jsimport { defineStore } from 'pinia'import { useUserStore } from './user'export const useCartStore = defineStore('cart', {  state: () => ({    items: []  }),  getters: {    totalItems: (state) => state.items.length,    totalPrice: (state) => {      return state.items.reduce((total, item) => total + item.price * item.quantity, 0)    }  },  actions: {    addToCart(product, quantity = 1) {      const userStore = useUserStore()      if (!userStore.isLoggedIn) {        throw new Error('请先登录')      }      const existingItem = this.items.find(item => item.id === product.id)      if (existingItem) {        existingItem.quantity += quantity      } else {        this.items.push({ ...product, quantity })      }    },    removeFromCart(productId) {      this.items = this.items.filter(item => item.id !== productId)    },    clearCart() {      this.items = []    }  }})

TypeScript 集成

Vue3 对 TypeScript 有很好的支持,可以显著提升代码质量和开发效率。

TypeScript与Vue3

5.1 项目配置

创建支持 TypeScript 的 Vue3 项目:

npm create vite@latest my-vue3-ts-app -- --template vue-ts

配置 tsconfig.json:

{  "compilerOptions": {    "target": "ESNext",    "useDefineForClassFields": true,    "module": "ESNext",    "moduleResolution": "Node",    "strict": true,    "jsx": "preserve",    "sourceMap": true,    "resolveJsonModule": true,    "isolatedModules": true,    "esModuleInterop": true,    "lib": ["ESNext", "DOM"],    "skipLibCheck": true,    "forceConsistentCasingInFileNames": true,    "paths": {      "@/*": ["./src/*"]    }  },  "include": ["src/**/*.ts", "src/**/*.d.ts", "src/**/*.tsx", "src/**/*.vue"],  "references": [{ "path": "./tsconfig.node.json" }]}

5.2 组件类型定义

为组件添加类型定义:

<template>  <div>    <h1>{{ title }}</h1>    <p>{{ message }}</p>    <button @click="handleClick">点击我</button>  </div></template><script setup lang="ts">import { defineProps, defineEmits } from 'vue'// 定义Props类型interface Props {  title: string  message?: string  count?: number}const props = defineProps<Props>({  title: {    type: String,    required: true  },  message: String,  count: {    type: Number,    default: 0  }})// 定义Emits类型const emit = defineEmits<{  'update:count': [value: number]  'click': [event: MouseEvent]}>()const handleClick = (event: MouseEvent) => {  emit('click', event)  emit('update:count', (props.count || 0) + 1)}</script>

5.3 响应式数据类型

为响应式数据添加类型:

<script setup lang="ts">import { ref, reactive, computed } from 'vue'// 基本类型const count = ref<number>(0)const message = ref<string>('Hello')const isActive = ref<boolean>(true)// 对象类型interface User {  id: number  name: string  email: string  age?: number}const user = ref<User | null>(null)const users = ref<User[]>([])// Reactive对象const state = reactive<{  count: number  user: User | null}>({  count: 0,  user: null})// 计算属性const doubleCount = computed<number>(() => count.value * 2)const userName = computed<string>(() => user.value?.name || 'Unknown')</script>

5.4 Pinia Store 类型

为 Pinia Store 添加类型:

// stores/user.tsimport { defineStore } from 'pinia'interface User {  id: number  name: string  email: string  token: string}interface UserState {  user: User | null  isLoggedIn: boolean  loading: boolean  error: string | null}export const useUserStore = defineStore('user', {  state: (): UserState => ({    user: null,    isLoggedIn: false,    loading: false,    error: null  }),  getters: {    userName: (state): string => state.user?.name || 'Guest',    isAdmin: (state): boolean => state.user?.email === 'admin@example.com'  },  actions: {    async login(email: string, password: string): Promise<void> {      this.loading = true      this.error = null      try {        // 模拟API请求        const response = await fetch('/api/login', {          method: 'POST',          body: JSON.stringify({ email, password })        })        const data = await response.json()        if (response.ok) {          this.user = data.user          this.isLoggedIn = true          localStorage.setItem('token', data.token)        } else {          throw new Error(data.message || '登录失败')        }      } catch (error) {        this.error = error instanceof Error ? error.message : '未知错误'        throw error      } finally {        this.loading = false      }    },    logout(): void {      this.user = null      this.isLoggedIn = false      localStorage.removeItem('token')    }  }})

5.5 路由类型

为 Vue Router 添加类型:

// router/index.tsimport { createRouter, createWebHistory, RouteRecordRaw } from 'vue-router'import HomeView from '../views/HomeView.vue'import AboutView from '../views/AboutView.vue'import UserView from '../views/UserView.vue'import NotFoundView from '../views/NotFoundView.vue'// 定义路由参数类型interface UserRouteParams {  id: string}const routes: RouteRecordRaw[] = [  {    path: '/',    name: 'home',    component: HomeView  },  {    path: '/about',    name: 'about',    component: AboutView  },  {    path: '/user/:id',    name: 'user',    component: UserView,    props: true  },  {    path: '/:pathMatch(.*)*',    name: 'not-found',    component: NotFoundView  }]const router = createRouter({  history: createWebHistory(import.meta.env.BASE_URL),  routes})export default router// 扩展路由类型declare module 'vue-router' {  interface RouteMeta {    requiresAuth?: boolean    title?: string    icon?: string  }}

在组件中使用类型化的路由:

<script setup lang="ts">import { useRoute, useRouter } from 'vue-router'// 获取类型化的路由const route = useRoute<{  params: {    id?: string  }  query: {    tab?: string    page?: string  }}>()const router = useRouter()// 类型安全的导航const goToUser = (id: number) => {  router.push({    name: 'user',    params: { id: id.toString() },    query: { tab: 'profile' }  })}</script>

实战项目

通过一个完整的实战项目来巩固所学知识。

6.1 项目规划

创建一个简单的待办事项应用(Todo App),包含以下功能:

  • 用户认证(登录 / 注册)
  • 待办事项管理(添加、编辑、删除、完成)
  • 分类和标签
  • 数据持久化

6.2 项目结构

todo-app/├── src/│   ├── assets/         # 静态资源│   ├── components/     # 组件│   │   ├── common/     # 通用组件│   │   ├── layout/     # 布局组件│   │   └── todo/       # 业务组件│   ├── composables/    # 组合式函数│   ├── router/         # 路由配置│   ├── stores/         # Pinia Store│   ├── types/          # 类型定义│   ├── utils/          # 工具函数│   ├── views/          # 页面组件│   ├── App.vue         # 根组件│   └── main.ts         # 入口文件├── package.json├── tsconfig.json└── vite.config.ts

6.3 核心实现

类型定义

// src/types/index.tsexport interface User {  id: string  name: string  email: string}export interface Todo {  id: string  title: string  description: string  completed: boolean  createdAt: Date  updatedAt: Date  tags: string[]}export interface Tag {  id: string  name: string  color: string}

用户 Store

// src/stores/user.tsimport { defineStore } from 'pinia'import { User } from '@/types'interface UserState {  user: User | null  isLoggedIn: boolean  loading: boolean  error: string | null}export const useUserStore = defineStore('user', {  state: (): UserState => ({    user: null,    isLoggedIn: false,    loading: false,    error: null  }),  actions: {    async login(email: string, password: string) {      this.loading = true      this.error = null      try {        // 模拟API请求        await new Promise(resolve => setTimeout(resolve, 1000))        this.user = {          id: '1',          name: '张三',          email: email        }        this.isLoggedIn = true        localStorage.setItem('user', JSON.stringify(this.user))      } catch (error) {        this.error = '登录失败,请检查用户名和密码'        throw error      } finally {        this.loading = false      }    },    logout() {      this.user = null      this.isLoggedIn = false      localStorage.removeItem('user')    },    init() {      const userData = localStorage.getItem('user')      if (userData) {        this.user = JSON.parse(userData)        this.isLoggedIn = true      }    }  }})

待办事项 Store

// src/stores/todo.tsimport { defineStore } from 'pinia'import { Todo } from '@/types'import { useUserStore } from './user'interface TodoState {  todos: Todo[]  loading: boolean  error: string | null}export const useTodoStore = defineStore('todo', {  state: (): TodoState => ({    todos: [],    loading: false,    error: null  }),  getters: {    activeTodos: (state) => state.todos.filter(todo => !todo.completed),    completedTodos: (state) => state.todos.filter(todo => todo.completed),    totalTodos: (state) => state.todos.length,    completedCount: (state) => state.todos.filter(todo => todo.completed).length  },  actions: {    async fetchTodos() {      const userStore = useUserStore()      if (!userStore.isLoggedIn) return      this.loading = true      this.error = null      try {        // 模拟API请求        await new Promise(resolve => setTimeout(resolve, 1000))        // 从本地存储获取数据        const todosData = localStorage.getItem('todos')        if (todosData) {          this.todos = JSON.parse(todosData)        } else {          this.todos = []        }      } catch (error) {        this.error = '获取待办事项失败'        throw error      } finally {        this.loading = false      }    },    async addTodo(todo: Omit<Todo, 'id' | 'createdAt' | 'updatedAt'>) {      const userStore = useUserStore()      if (!userStore.isLoggedIn) return      this.loading = true      this.error = null      try {        const newTodo: Todo = {          id: Date.now().toString(),          ...todo,          createdAt: new Date(),          updatedAt: new Date()        }        this.todos.push(newTodo)        this.saveTodos()      } catch (error) {        this.error = '添加待办事项失败'        throw error      } finally {        this.loading = false      }    },    async updateTodo(id: string, updates: Partial<Todo>) {      const userStore = useUserStore()      if (!userStore.isLoggedIn) return      this.loading = true      this.error = null      try {        const index = this.todos.findIndex(todo => todo.id === id)        if (index !== -1) {          this.todos[index] = {            ...this.todos[index],            ...updates,            updatedAt: new Date()          }          this.saveTodos()        }      } catch (error) {        this.error = '更新待办事项失败'        throw error      } finally {        this.loading = false      }    },    async deleteTodo(id: string) {      const userStore = useUserStore()      if (!userStore.isLoggedIn) return      this.loading = true      this.error = null      try {        this.todos = this.todos.filter(todo => todo.id !== id)        this.saveTodos()      } catch (error) {        this.error = '删除待办事项失败'        throw error      } finally {        this.loading = false      }    },    saveTodos() {      localStorage.setItem('todos', JSON.stringify(this.todos))    }  }})

路由配置

// src/router/index.tsimport { createRouter, createWebHistory, RouteRecordRaw } from 'vue-router'import HomeView from '../views/HomeView.vue'import LoginView from '../views/LoginView.vue'import RegisterView from '../views/RegisterView.vue'import TodoListView from '../views/TodoListView.vue'import TodoDetailView from '../views/TodoDetailView.vue'import NotFoundView from '../views/NotFoundView.vue'import { useUserStore } from '@/stores/user'const routes: RouteRecordRaw[] = [  {    path: '/',    name: 'home',    component: HomeView  },  {    path: '/login',    name: 'login',    component: LoginView,    meta: {      requiresAuth: false    }  },  {    path: '/register',    name: 'register',    component: RegisterView,    meta: {      requiresAuth: false    }  },  {    path: '/todos',    name: 'todo-list',    component: TodoListView,    meta: {      requiresAuth: true    }  },  {    path: '/todos/:id',    name: 'todo-detail',    component: TodoDetailView,    meta: {      requiresAuth: true    },    props: true  },  {    path: '/:pathMatch(.*)*',    name: 'not-found',    component: NotFoundView  }]const router = createRouter({  history: createWebHistory(import.meta.env.BASE_URL),  routes})// 路由守卫router.beforeEach((to, from, next) => {  const userStore = useUserStore()  const requiresAuth = to.meta.requiresAuth !== false  if (requiresAuth && !userStore.isLoggedIn) {    next('/login')  } else if (!requiresAuth && userStore.isLoggedIn) {    next('/todos')  } else {    next()  }})export default router

学习资源推荐

7.1 官方文档

7.2 在线课程

7.3 社区资源

7.4 书籍推荐

  • 《Vue.js 设计与实现》- 深入理解 Vue3 内部原理
  • 《TypeScript 实战》- 掌握 TypeScript 在 Vue 中的应用
  • 《前端架构设计》- 学习大型 Vue 项目的架构设计

总结

通过本指南的学习,你已经掌握了 Vue3 开发的核心技能:

  1. Vue3 基础语法:模板语法、响应式数据、指令系统
  2. 组合式 API:setup 函数、计算属性、监听器、生命周期
  3. Vue Router:路由配置、导航守卫、参数传递
  4. Pinia:状态管理、Store 组合、数据持久化
  5. TypeScript:类型定义、类型安全、开发效率

Vue3 作为现代前端开发的重要工具,具有以下优势:

  • 性能优秀:重写的响应式系统,性能提升显著
  • API 友好:组合式 API 提供了更好的代码组织方式
  • 类型安全:原生支持 TypeScript,提升代码质量
  • 生态完善:丰富的官方库和第三方插件
  • 社区活跃:活跃的开发者社区和丰富的学习资源

建议你通过实际项目来巩固所学知识,从简单的应用开始,逐步挑战更复杂的项目。持续学习和实践是掌握 Vue3 的关键。

祝你在 Vue3 的学习之旅中取得成功!

声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系QQ号码:1405296我们进行处理。

给TA打赏
共{{data.count}}人
人已打赏
学习资源技术教程上新

Vue3 从下载引用到本地环境运行的详细技术指南

2025-12-25 14:52:31

大白大白日常

《我的猫主子 “大白”:一只把阳光睡成日常的 “白团子”》

2025-12-6 17:48:39

0 条回复 A文章作者 M管理员
    暂无讨论,说说你的看法吧
个人中心
购物车
优惠劵
今日签到
有新私信 私信列表
搜索