Vue 组件中获取 Vuex state 数据的三种核心方式

这段代码展示了 Vue 组件中获取 Vuex state 数据的三种核心方式,核心差异在于「响应式表现」「数据更新机制」「适用场景」,

下面逐一拆解每种方式的原理、特点和为什么会有这些区别:

html 复制代码
<template>
  <div class="about">
    <h2>直接取的</h2>
    <!--方式1: 直接取-->
    <p>取出Vuex的数据,user: {{this.$store.state.user}}</p>
    <p>取出Vuex的数据,token: {{this.$store.state.token}}</p>
    <hr>
    <h2>data中获取的</h2>
    <!--方式2: 在data中获取-->
    <p>取出Vuex的数据,user: {{user}}</p>
    <p>取出Vuex的数据,token: {{token}}</p>
    <hr>
    <h2>调用mutations中的方法修改token</h2>
    <input type="text" v-model="newToken">
    <button @click="changeToken">修改token</button>
    <h2>计算属性中获取的</h2>
    <p>取出Vuex的数据,token: {{token2}}</p>
  </div>
</template>
<script>
export default {
  name: 'AboutView',
  data() {
    return {
      // 可以在data中直接获取Vuex中的数据
      user: this.$store.state.user,
      // token: this.$store.state.token,
      newToken:''
    }
  },
  // 建议使用计算属性取出Vuex的数据,而不是data
  computed:{
    token2(){
      return this.$store.state.token
    }
  }
  ,
  methods: {
    changeToken(){
      // 调用mutations中的方法,修改token
      // this.$store.commit("mutations中定义的方法名", "调用时传递的参数")
      this.$store.commit("setToken", this.newToken)
    }
  }
}
</script>

一、方式 1:模板中直接取 this.$store.state.xxx

写法 html

javascript 复制代码
<p>取出Vuex的数据,user: {{this.$store.state.user}}</p>
核心原理

模板渲染时实时访问 Vuex 的 state 对象属性 ------Vuex 的 state 本身是响应式的,模板每次渲染 / 更新都会重新读取 $store.state.xxx 的最新值。

关键特点
  1. 完全响应式 :当 state 中的 user/token 被修改(比如通过 mutation),模板会立刻同步更新;
  2. 无缓存 :每次模板重渲染都会重新读取 state(性能影响可忽略,除非高频渲染);
  3. 语法简单但冗余 :直接写 this.$store.state.xxx 直观,但多次使用会导致模板代码臃肿,维护性差。
适用场景
  • 临时调试、快速验证数据;
  • 只在模板中少量使用 state 数据的简单场景。
为什么能实时更新?

Vuex 的 state 是基于 Vue 的响应式对象实现的,模板中访问 $store.state.xxx 会触发 Vue 的「依赖收集」,当 state 数据变化时,Vue 会通知模板重新渲染。

二、方式 2:在 data 中获取 this.$store.state.xxx

写法 js

javascript 复制代码
data() {
  return {
    user: this.$store.state.user, // 初始化时赋值
    newToken:''
  }
}
核心原理

data 中的属性在组件实例化时(beforeCreate/created 阶段)只赋值一次 ------ 把当时 $store.state.user 的「初始值」拷贝给 data.user,后续 state 变化不会同步到 data.user

关键特点
  1. 非响应式 :这是最核心的问题!比如通过 changeToken 修改了 state.token,但 data 中如果定义了 token: this.$store.state.token,模板里的 {``{token}} 永远是初始化的旧值,不会更新;
  2. 数据是 "拷贝"data.user 只是拿到了 state.user 初始化时的取值(如果是基本类型,是值拷贝;如果是引用类型,是地址拷贝,但 state 本身的响应式不会传递给 data 的属性);
  3. 模板写法简洁 :模板中只需写 {``{user}},无需写冗长的 $store.state
为什么不推荐?

data 的设计初衷是存储「组件自身的局部状态」,其初始化逻辑只执行一次,无法感知 Vuex state 的后续变化 ------ 这会导致 "数据不一致" 的 bug(比如 state 改了,但组件显示的还是旧值)。

适用场景

几乎不推荐使用 ,除非能 100% 确定 state 中的该数据在组件生命周期内永远不会变化(比如静态常量)。

三、方式 3:在 computed(计算属性)中获取 this.$store.state.xxx

重要用法: 一般从state中取出的数据要放在computed中而不是data中!

写法 js

javascript 复制代码
computed:{
  token2(){
    return this.$store.state.token
  }
}
核心原理

计算属性会「依赖收集」------ 它会监听 this.$store.state.token 的变化,当 state.token 被修改时,计算属性会自动重新计算返回最新值,并触发模板更新。同时,计算属性有「缓存特性」:只要依赖的 state.token 不变,多次访问 token2 只会执行一次计算。

关键特点
  1. 完全响应式state.token 变化,token2 会同步更新,模板也会跟着更;
  2. 有缓存 :提升性能(比如多次在模板中用 {``{token2}},不会重复读取 state);
  3. 模板简洁 + 可维护 :模板写 {``{token2}} 即可,且计算属性可以集中管理 state 数据的读取逻辑(比如后续需要对 token 做格式化,只需改计算属性,无需改所有模板);
  4. 支持扩展 :可以在计算属性中对 state 数据做派生 / 格式化(比如 return this.$store.state.token || '默认值')。
为什么是最佳实践?

计算属性完美结合了「响应式」和「简洁性」,既解决了直接取值的模板冗余问题,又避免了 data 取值的非响应式坑,同时还能通过缓存优化性能。

三种方式核心对比表

方式 响应式 缓存 模板简洁度 维护性 推荐度
模板直接取 $store.state ✅ 是 ❌ 无 ❌ 冗余 ⭐⭐
data 中赋值 ❌ 否 ❌ 无 ✅ 简洁 极差
computed 中取值 ✅ 是 ✅ 有 ✅ 简洁 ⭐⭐⭐

补充:修改 state 的逻辑(changeToken 方法)

代码中 changeToken 调用 this.$store.commit("setToken", this.newToken) 是 Vuex 规定的唯一合法修改 state 的方式(通过 mutation),这和 "取值方式" 的呼应:

  • 不管用哪种方式取值,只要通过 mutation 修改了 state.token
    • 方式 1、方式 3 会实时更新;
    • 方式 2 永远不会更新(因为是初始化一次的拷贝)。

总结

  • 临时调试用「模板直接取」;
  • 绝对不要用「data 中取值」(除非数据永不改);
  • 正式开发优先用「计算属性取值」(响应式、高性能、易维护);
  • 进阶优化:还可以用 Vuex 提供的 mapState 辅助函数简化计算属性写法(比如 ...mapState(['user', 'token'])),进一步减少代码冗余。
相关推荐
崔庆才丨静觅17 小时前
hCaptcha 验证码图像识别 API 对接教程
前端
passerby606118 小时前
完成前端时间处理的另一块版图
前端·github·web components
掘了18 小时前
「2025 年终总结」在所有失去的人中,我最怀念我自己
前端·后端·年终总结
崔庆才丨静觅18 小时前
实用免费的 Short URL 短链接 API 对接说明
前端
崔庆才丨静觅18 小时前
5分钟快速搭建 AI 平台并用它赚钱!
前端
崔庆才丨静觅19 小时前
比官方便宜一半以上!Midjourney API 申请及使用
前端
Moment19 小时前
富文本编辑器在 AI 时代为什么这么受欢迎
前端·javascript·后端
崔庆才丨静觅19 小时前
刷屏全网的“nano-banana”API接入指南!0.1元/张量产高清创意图,开发者必藏
前端
剪刀石头布啊19 小时前
jwt介绍
前端
爱敲代码的小鱼19 小时前
AJAX(异步交互的技术来实现从服务端中获取数据):
前端·javascript·ajax