响应式数据

Vue3 一切自动更新都建立在"响应式数据"之上:数据一变,用到它的界面立刻跟着变。实现响应式有两个主角——ref 与 reactive。理解它们的区别与适用场景,是吃透 Vue3 的关键。

为什么需要响应式

传统 JS 中改一个变量,页面不会自动更新,得手动操作 DOM:

let count = 0
count = 1        // 页面毫无反应,还要自己找元素去改

Vue3 里把数据变成"响应式"后,赋值即触发界面更新,代码只需关注数据本身。

ref:适合所有值

ref 可以包装基本类型与对象,读取、修改都要通过 .value:

<script setup>
import { ref } from 'vue'

const count = ref(0)              // 基本类型
const user = ref({ name: '张三' })  // 对象也可以

count.value++                     // 修改用 .value
console.log(count.value)          // 输出:1

user.value.name = '李四'           // 改对象属性先取 .value
console.log(user.value.name)      // 输出:李四
</script>

<template>
  <p>{{ count }}</p>              <!-- 模板中自动解包,无需 .value -->
</template>

reactive:只接受对象

reactive 接收对象/数组并返回深层响应式代理,读写直接点属性即可:

import { reactive } from 'vue'

const state = reactive({
  list: [],
  keyword: ''
})

state.keyword = 'vue'             // 直接赋值
state.list.push('响应式教程')       // 嵌套数组同样响应式
console.log(state.keyword)        // 输出:vue

效果:模板里引用 state.keyword 的地方会随赋值自动更新。

各自该怎么选

  • 基本类型(数字/字符串/布尔)只能用 ref;
  • 对象、数组两者皆可:想要显式的 .value 风格用 ref,想少打字用 reactive;
  • 需要整体替换对象时 reactive 不方便(直接换引用会丢失响应式),用 ref 更稳妥;
  • 组合式函数对外返回数据时习惯用 ref,便于解构后仍保持响应式。

解构 reactive 会丢失响应式

直接解构 reactive 得到的变量只是"快照",不再与源对象联动:

const { keyword } = state
keyword = 'xxx'       // 改了它,state.keyword 不会变!

需要保持联动,请用 toRefs 转换:

import { toRefs } from 'vue'

const { keyword } = toRefs(state)   // keyword 变成 ref
keyword.value = 'vue-router'        // state.keyword 同步变化

小结

一句话总结:基本类型用 ref、对象优先 reactive、解构保持响应式用 toRefs。把这两个 API 用熟,后续学 computed、watch、Pinia 都会事半功倍。

笔记加载中…