Vuex状态机的快速了解与实例应用

目录
  • 一. 速识概念:
    • 1. 组件之间共享数据的方式:
    • 2. vuex是什么:
  • 二. 基本使用:
  • 三.创建项目:
  • 四. 讲解前提:
  • 五.核心概念:
    • 1.state:
      • 1.1 组件中访问state的第一种方式:
      • 1.2 组件中访问state的第二种方式:
    • 2. mutation:
      • 2.1 触发mutation的第一种方式:
      • 2.2 触发mutation并传参数:
      • 2.1 触发mutation的第二种方式:
    • 3.Action:
      • 3.1 触发Action的第一种方式:
      • 3.2 触发Action异步任务并传参数:
      • 3.3 触发Action的第二种方式:
    • 4. Getter:
      • 4.2触发getters的第二种方式:
  • 六.总结:

一. 速识概念:

1. 组件之间共享数据的方式:

通常有以下几种方式:

  1. 父向子传值:v-bind 属性绑定
  2. 子向父传值:v-on 事件绑定
  3. 兄弟组件之间共享数据:EventBus

2. vuex是什么:

  1. 按照官方的话来说,Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。Vuex 也集成到 Vue 的官方调试工具 devtools extension (opens new window),提供了诸如零配置的 time-travel 调试、状态快照导入导出等高级调试功能。
  2. 简单来说,Vuex就是实现组件全局状态(数据)管理的一种机制,可以方便的实现组件之间数据的共享。

3.使用vuex优点:

  1. 能够在vuex中集中管理共享的数据,易于开发和后期维护。
  2. 能够高效地实现组件之间的数据共享, 提高开发效率。
  3. 存储在vuex中的数据都是响应式的,能够实时保持数据与页面的同步。
  4. 解决了非父子组件的消息传递(将数据存放在state中)。
  5. 减少了AJAX请求次数,有些情景可以直接从内存中的state获取。

  一般情况下,只有组件之间共享的数据,才有必要存储到vuex中。而对于组件中的私有数据,就没必要了,依旧存储在组件自身的data中即可。当然,如果你想要都存在vuex中也是可以的。

二. 基本使用:

1.安装依赖包:

npm install vuex --save

2.导入依赖包:

import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

3.创建store对象:

import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

const store = new Vuex.Store({
//state中存放的就是全局共享的数据
  state: {
    count: 0
  }
})

4. 将store对象挂载到vue实例中:

new Vue({
  el: '#app',
  store
})

此时所有组件就可以从store中获取数据了。

三.创建项目:

下面为创建一个vue项目流程,后面会有案例:

(1)打开cmd窗口输入 vue ui 打开vue的可视化面板:

(2)选择新建项目路径:

(3)命名:

(4)手动选择配置,注意用的是vue2版本:

(5)创建:

(6)下一步:

(7)创建成功,到对应目录打开vscode开始编程:

(8)运行项目:

四. 讲解前提:

前提(注意):

   写一个计数器小案例,从案例配合概念能更快上手vuex。所以下面核心概念中的代码部分是基于这个小案例来演示的。目标:写两个子组件,有一个公共count值,在父组件中,其中一个组件实现点击后count值减1,一个组件实现点击后count值增1。

父组件 App.vue 初始代码:

<template>
  <div id="app">
       <my-add></my-add>
       <p>--------------------</p>
       <my-reduce></my-reduce>
  </div>
</template>

<script>
// 引入组件
import Add from './components/Add.vue'
import Reduce from './components/Reduce.vue'
export default {
  name: 'App',
  data() {
    return {

    }
  },
  components: {
    'my-add': Add,
    'my-reduce': Reduce
  }

}
</script>

子组件Add.vue初始代码:

<template>
    <div>
        <p>count值为:</p>
           <button>+1</button>
    </div>

</template>
<script>
  export default{
      data() {
          return {

          }
      },
  }
</script>

子组件Reduce.vue初始代码:

<template>
    <div>
         <p>count值为:</p>
           <button>-1</button>
    </div>
</template>
<script>
  export default{
      data() {
          return {

          }
      },
  }
</script>

store对象初始代码为:

import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

export default new Vuex.Store({
  state: {
    count: 0
  }
})

初始效果:

五.核心概念:

1.state:

   按照官方的话来说,如下:Vuex 使用单一状态树——是的,用一个对象就包含了全部的应用层级状态。至此它便作为一个“唯一数据源 (SSOT)”而存在。这也意味着,每个应用将仅仅包含一个 store 实例。

   简单来说,就是State提供唯一的公共数据源, 所有共享的数据都要统一放到Store的State中进行存储。

1.1 组件中访问state的第一种方式:

组件中直接输入以下命令:

this.$store.state.引用的数据名字

如在Add.vue子组件中引用:

<template>
    <div>
        <p>count值为:{{this.$store.state.count}}</p>
           <button>+1</button>
    </div>
</template>
//下面部分代码跟前面一样无改变,所以省略了

看效果,显示了count的值为0:

1.2 组件中访问state的第二种方式:

(1)从 vuex 中按需导入 mapState 函数

import { mapState } from 'vuex'

(2)通过刚才导入的mapState函数,将当前组件需要的全局数据,映射为当前组件的computed计算属性:

computed: {
   ...mapState([count])
}

小知识:computed用来监控自己定义的变量,该变量不在data里面声明,直接在computed里面定义,然后就可以在页面上进行双向数据绑定展示出结果或者用作其他处理;

如在Reduce.vue子组件中引用:

<template>
    <div>
         <p>count值为:{{count}}</p>
           <button>-1</button>
    </div>
</template>
<script>
import {mapState} from 'vuex'
  export default{
      data() {
          return {

          }
      },
      computed: {
         ...mapState(['count'])
      }
  }
</script>

看效果,同样显示了count的值为0:

2. mutation:

   按照官方的话来说,更改 Vuex 的 store 中的状态的唯一方法是提交 mutation。Vuex 中的 mutation 非常类似于事件:每个 mutation 都有一个字符串的 事件类型 (type) 和 一个 回调函数 (handler)。这个回调函数就是我们实际进行状态更改的地方,并且它会接受 state 作为第一个参数。

   简单来说就是Mutation用于变更Store中的数据。
①只能通过mutation变更Store数据,不可以直接操作Store中的数据。
②通过这种方式虽然操作起来稍微繁琐一些,但是可以集中监控所有数据的变化。

   比如,要实现count值自增加1的操作,那就在先motations里定义一个自增加1的函数。然后对应子组件想用,该组件就直接引入mutation并调用对应的函数就好。

如下,Add.vue子组件要实现自增加1功能:

先在状态机里的mutations里定义一个能实现自增的函数add:

export default new Vuex.Store({
  state: {
    count: 0
  },
  mutations: {
    //自增加1函数
    add(state){
      state.count++
    }
  }
})

2.1 触发mutation的第一种方式:

Add.vue子组件里给按钮绑定点击事件,并触发mutation:

<template>
    <div>
        <p>count值为:{{this.$store.state.count}}</p>
           <button @click="btnAdd">+1</button>
    </div>

</template>
<script>
  export default{
      data() {
          return {

          }
      },
      methods: {
          btnAdd() {
              // 第一种引入mutation的方式,触发add函数
              this.$store.commit('add')
          }
      }
  }
</script>

看效果实现了点击自增:

2.2 触发mutation并传参数:

当然,当组件里调用mutation里函数时,也是可以传参数的。

比如,有一个自增函数,但增多少看调用时传入的参数:

export default new Vuex.Store({
  state: {
    count: 0
  },
  mutations: {
    // 传入参数,第一个一定是state,第二个为传入的参数
    //自增加 n 的函数
    addN(state,n){
      state.count+= n
    }
  }
})

对应组件调用时要传入参数:

  methods: {
          btnAdd2() {
              // 引入mutation的方式,触发addN函数
              // 并传参,自增加6吧
              this.$store.commit('addN',6)
          }
      }

2.1 触发mutation的第二种方式:

(1)从 vuex 中按需导入 mapMutations 函数

import { mapMutations } from 'vuex'

(2)通过刚才导入的mapMutations函数,将需要的mutations函数,映射为当前组件的methods方法:

methods: {
   ...mapMutations(['add','addN'])
}

实战,实现Reduce.vue组件的点击自减1的功能要求:

状态机添加自减函数:

export default new Vuex.Store({
  state: {
    count: 0
  },
  mutations: {
    //自增加1函数
    add(state){
      state.count++
    },
    // 自减1的函数
    sub(state){
      state.count--
    }
  }
})

Reduce.vue组件点击按钮实现自减1:

<template>
    <div>
         <p>count值为:{{count}}</p>
           <button @click="btnSub">-1</button>
    </div>
</template>
<script>
//导入
import {mapState,mapMutations} from 'vuex'
  export default{
      data() {
          return {

          }
      },
      computed: {
         ...mapState(['count'])
      },
      methods: {
          // 映射mutation里的sub函数
          ...mapMutations(['sub']),
          // 要自减,调用sub函数
          btnSub(){
             this.sub()
          }
      }
  }
</script>

看效果:

3.Action:

   至此,第四大点里的案例已经完成,已经实现了自增和自减,现在对案例做改进,要我们点击按钮一秒后再自增和自减,该怎么实现?可以在状态机里的mutation里的函数是加一个1秒定时器吗,这肯定是不行的,因为mutation里不支持异步操作,那咋办,当当当,Action闪亮登场。

    Action 可以包含任意异步操作,所以它用来处理异步任务。
   Action 提交的是 mutation,而不是直接变更状态。记住它并不能直接修改state里的数据,只有mutation能修改。就是说,如果通过异步操作变更数据,必须通过Action,而不能使用Mutation,但是在Action中还是要通过触发Mutation的方式间接变更数据。

先在状态机里定义Action:

export default new Vuex.Store({
  state: {
    count: 0
  },
  mutations: {
    //自增加1函数
    add(state){
      state.count++
    },
    // 自减1的函数
    sub(state){
      state.count--
    }
  },
  // 定义action,里面的addAsync函数实现1秒后执行mutation里的add函数
   actions: {
    addAsync(context) {
      setTimeout(()=>{
      // 必须通过context.commit()触发mutation才行
         context.commit('add')
    },1000)
  }
 }
})

Action 函数接受一个与 store 实例具有相同方法和属性的 context 对象,因此你可以调用 context.commit 提交一个 mutation。

3.1 触发Action的第一种方式:

更改组件Add.vue代码,引入Action,实现异步自增操作。

<template>
    <div>
        <p>count值为:{{this.$store.state.count}}</p>
           <button @click="btnAdd">+1</button>
    </div>

</template>
<script>
  export default{
      data() {
          return {

          }
      },
      methods: {
          btnAdd() {
              // 第一种引入Action的方式,触发addAsync函数
              // 这里的dispatch专门用来调用action函数
              this.$store.dispatch('addAsync')
          }
      }
  }
</script>

看效果,实现1秒后自增:

3.2 触发Action异步任务并传参数:

当然,当组件里调用action里函数时,也是可以传参数的。

比如,有一个点击1秒后才执行的自增函数,但增多少看调用时传入的参数:

定义:

export default new Vuex.Store({
  state: {
    count: 0
  },
  mutations: {
   // 传入参数,第一个一定是state,第二个为传入的参数
    //自增加 n 的函数
    addN(state,n){
      state.count+= n
    }
  },
   actions: {
    // 有参数 n,这个n又传给了mutation里的addN函数
    addNAsync(context,n) {
      setTimeout(()=>{
         context.commit('addN',n)
    },1000)
  }
 }
})

对应组件调用时要传入参数:

  methods: {
          btnAdd2() {
              // 调用dispatch函数
              // 触发action时传参数,为 6 吧,表示自增6
              this.$store.dispatch('addNAsync',6)
          }
      }

3.3 触发Action的第二种方式:

(1)从 vuex 中按需导入 mapActions 函数

import { mapActions } from 'vuex'

(2)通过刚才导入的mapActions函数,将需要的actions函数,映射为当前组件的methods方法:

methods: {
   ...mapActions(['add','addN'])
}

实战,实现Reduce.vue组件的点击一秒后自减1的功能要求:

定义actions里的subAsync为一秒后自减函数:

export default new Vuex.Store({
  state: {
    count: 0
  },
  mutations: {
    //自增加1函数
    add(state){
      state.count++
    },
    // 自减1的函数
    sub(state){
      state.count--
    }
  },
   actions: {
    addAsync(context) {
      setTimeout(()=>{
         context.commit('add')
    },1000)
  },
   subAsync(context) {
      setTimeout(()=>{
         context.commit('sub')
    },1000)
  }
 }
})

更改Reduce.vue代码,实现功能:

<template>
    <div>
         <p>count值为:{{count}}</p>
           <button @click="btnSub">-1</button>
    </div>
</template>
<script>
//导入
import {mapState,mapActions} from 'vuex'
  export default{
      data() {
          return {

          }
      },
      computed: {
         ...mapState(['count'])
      },
      methods: {
          // 映射Action里的函数
          ...mapActions(['subAsync']),
          // 要自减,调用subAsync函数
          btnSub(){
             this.subAsync()
          }
      }
  }
</script>

看效果:

4. Getter:

    Getter用于对Store中的数据进行加工处理形成新的数据。且要注意的是它并不会修改state中的数据。
①Getter 可以对Store中已有的数据加工处理之后形成新的数据,类似Vue的计算属性。
②Store 中数据发生变化,Getter 的数据也会跟着变化。

如,有一个返回当前count+1的getter函数:

export default new Vuex.Store({
  state: {
    count: 0
  },
 getters: {
    showNum(state){
      return`当前count值加1为:${state.count+1}`
    }
  }
})

4.1 触发getters的第一种方式:

this.$store.getters.名称

在App.vue组件中显示:

<template>
  <div id="app">
       <my-add></my-add>
       <p>--------------------</p>
       <my-reduce></my-reduce>
       <p>--------------------</p>
       <h3>{{this.$store.getters.showNum}}</h3>
  </div>
</template>

效果:

4.2触发getters的第二种方式:

(1)从 vuex 中按需导入 mapGetters 函数

import { mapGetters } from 'vuex'

(2)通过刚才导入的mapGetters函数,将当前组件需要的全局数据,映射为当前组件的computed计算属性:

computed: {
   ...mapGetters(['showNum'])
}

还是在App.vue中使用把:

<template>
  <div id="app">
       <my-add></my-add>
       <p>--------------------</p>
       <my-reduce></my-reduce>
       <p>--------------------</p>
       <h3>{{showNum}}</h3>
  </div>
</template>

<script>
// 引入组件
import Add from './components/Add.vue'
import Reduce from './components/Reduce.vue'
// 导入 mapGetters函数
import {mapGetters} from 'vuex'
export default {
  name: 'App',
  data() {
    return {

    }
  },
  components: {
    'my-add': Add,
    'my-reduce': Reduce
  },
  // 引入 getter
  computed: {
    ...mapGetters(['showNum'])
  }

}
</script>

看,一样的效果:

六.总结:

到此这篇关于Vuex状态机的快速了解与实例应用的文章就介绍到这了,更多相关Vuex状态机应用内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • Vue的Flux框架之Vuex状态管理器

    学习vue之前,最重要是弄懂两个概念,一是"what",要理解vuex是什么:二是"why",要清楚为什么要用vuex. Vuex是什么? Vuex 类似 React 里面的 Redux 的状态管理器,用来管理Vue的所有组件状态. 为什么使用Vuex? 当你打算开发大型单页应用(SPA),会出现多个视图组件依赖同一个状态,来自不同视图的行为需要变更同一个状态. 遇到以上情况时候,你就应该考虑使用Vuex了,它能把组件的共享状态抽取出来,当做一个全局单例模式进行管理

  • 详解Vuex管理登录状态

    又仔细看了一遍vuex的文档,还是云里雾里的,不过至少明白它是一个专门管理状态的,根据数据状态的改变可以驱动视图更新,既然是这样那至少登录注册是一种状态,就用登录来做测试,学习vuex,不过话说回来,既然专门管理状态,那我至少要仔细推敲一下这个learn的学习项目有那些状态逻辑. 1.据说储存的vuex store里面的状态是临时的,右键刷新一下页面这些状态就销毁了(这是据说,请大神解惑我也没办法证实),如果是这样的话,我的用户状态user还是应该要写入sessionStorage,不然登录了的

  • 说说如何使用Vuex进行状态管理(小结)

    1 为什么需要状态管理 一个 Vue 组件分为数据(model)与视图(view).当通过 methods 中的方法更新数据时,视图也会自动更新. message.vue <template> <div> {{message}} <button @click="changeMessage">改变内容</button> </div> </template> <script> export default

  • 浅谈vuex 闲置状态重置方案

    前言 大型单页应用(后面都是指spa),我们往往会通过使用状态管理器 vuex 去解决组件间状态共享与状态传递等问题.这种应用少则几十个单页,多则上百个单页.随着路由的频繁切换,每个路由对应的 vuex 中的状态将越来越多.为了做到页面的极致优化,我们需要将那些闲置的状态重置,以减小占用的内存空间. 什么状态可以重置 vuex 强调采用集中式存储管理应用的所有组件的状态,但是我们真把所有的状态都放到 store 中去处理,你会发现开发起来非常痛苦.这里如果想很好的把控哪些数据需要放到 store

  • 详解Vue中状态管理Vuex

    vuex是一个专门为vue.js设计的状态管理模式,并且也可以使用devtools进行调试. 在vuex出现之前,vue里面的状态是属于'单向数据流'.举个官网的例子: new Vue({ // state data () { return { count: 0 } }, // view template: `<div>{{ count }} </div`, // actions methods: { increment () { this.count++ } } }) 其中 state

  • Vuex状态机的快速了解与实例应用

    目录 一. 速识概念: 1. 组件之间共享数据的方式: 2. vuex是什么: 二. 基本使用: 三.创建项目: 四. 讲解前提: 五.核心概念: 1.state: 1.1 组件中访问state的第一种方式: 1.2 组件中访问state的第二种方式: 2. mutation: 2.1 触发mutation的第一种方式: 2.2 触发mutation并传参数: 2.1 触发mutation的第二种方式: 3.Action: 3.1 触发Action的第一种方式: 3.2 触发Action异步任务

  • Android 实现夜间模式的快速简单方法实例详解

    ChangeMode 项目地址:ChangeMode Implementation of night mode for Android. 用最简单的方式实现夜间模式,支持ListView.RecyclerView. Preview Usage xml android:background="?attr/zzbackground" app:backgroundAttr="zzbackground"//如果当前页面要立即刷新,这里传入属性名称 比如 R.attr.zzb

  • web前端vue之vuex单独一文件使用方式实例详解

    Vuex 是什么? Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式.它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化.Vuex 也集成到 Vue 的官方调试工具 devtools extension,提供了诸如零配置的 time-travel 调试.状态快照导入导出等高级调试功能. 上次我用了一个加减的例子为大家讲解vuex的基本的使用方式,和在什么样的情况下使用.上次还是在一个组件内把这个例子简单的展示了下,这次我把vuex抽离出来一个

  • vue中在vuex的actions中请求数据实例

    我废话不多说了,直接上代码吧! actions.js getCertificationStatus(context, {vm:vm,type:type}){ return new Promise((resolve, reject) => { axios.post('/realNameUtils/gotoStatusPage') .then((res)=>{ context.commit('certificationStatus',res.data.content) if(type=='1'){

  • vuex actions异步修改状态的实例详解

    actions异步修改状态与mutations同步修改状态是两个容易混淆的概念,因为两者在执行上,很难测试出两者的差别,而我们要区别它们两,首先你得区分同步与异步,我的理解是,同步更像是一条流水线作业,而异步则更像是多条,例子你比如打电话,我们通常是我打给我妈,打完之后,再跟我爸打,而异步更像是某聊天工具,你既可以跟你爸聊,又可以跟你妈聊,你跟你妈聊可以在你爸的后面,也可以在他前面,你爸也是 而actions与mutations的区别就在此,mutations是你进行用百度钱包买一件商品时,你必

  • Vuex之理解Getters的用法实例

    1.什么是getters 在介绍state中我们了解到,在Store仓库里,state就是用来存放数据,若是对数据进行处理输出,比如数据要过滤,一般我们可以写到computed中.但是如果很多组件都使用这个过滤后的数据,比如饼状图组件和曲线图组件,我们是否可以把这个数据抽提出来共享?这就是getters存在的意义.我们可以认为,[getters]是store的计算属性. 2.如何使用 定义:我们可以在store中定义getters,第一个参数是state const getters = {sty

  • Vuex之理解Mutations的用法实例

    1.什么是mutations? 上一篇文章说的getters是为了初步获取和简单处理state里面的数据(这里的简单处理不能改变state里面的数据),Vue的视图是由数据驱动的,也就是说state里面的数据是动态变化的,那么怎么改变呢,切记在Vuex中store数据改变的唯一方法就是mutation! 通俗的理解mutations,里面装着一些改变数据方法的集合,这是Veux设计很重要的一点,就是把处理数据逻辑方法全部放在mutations里面,使得数据和视图分离. 2.怎么用mutation

  • C#实现的SN快速输入工具实例

    本文实例讲述了C#实现的SN快速输入工具的方法.分享给大家供大家参考.具体实现方法分析如下: 一般软件都要输入序列号(SN),而大家平时用的最多的恐怕是盗版软件,通常盗版软件的序列号(SN)都保存成:XXXXX-XXXXX-XXXX-XXXX的形式. 而软件输入序列号的地方通常都是几个文本框(TextBox)组成.一个个的将XXXXX复制到文本框将非常麻烦.于是SN快速输入工具便由此产生了. 当然这些都和我的编写这个程序的原因无关.我编写这个程序的原因纯粹是因为有个网友和他舅舅打赌说要编写个程序

  • Vuex利用state保存新闻数据实例

    回顾 以前我们在做这个新闻列表的时候,是一个写死的数据 export default{ data(){ return{ newslist:[ {newsid:"101",pubtime:"2016-10-29",title:"探索之路",desc:"是手机团队的探索之路"}, {newsid:"102",pubtime:"2016-10-28",title:"系统之战"

  • Vuex之理解state的用法实例

    1.什么是state? 上一篇文章说了,Vuex就是提供一个仓库,仓库里面放了很多对象.其中state就是数据源存放地,对应于与一般Vue对象里面的data(后面讲到的actions和mutations对应于methods). 响应书存储:state里面存放的数据是响应式的,Vue组件从store中读取数据,若是store中的数据发生改变,依赖这个数据的组件也会发生更新.(这里"状态"="数据"),也就是是说数据和视图是同步的. 2.局部状态 获取:在Vue组件中获

随机推荐