vue mutations与actions的区别

关于 mutations与actions的区别,网上有很多文章,大多是照着vue.js的教程再来一波!!因为最近接手vue项目,自己之前vue的知识点掌握也不深,就此机会把这个知识点再深挖一下。

使用vuex进行状态管理时,使用mutations来进行state的状态变更。其中一个要求就是mutations中的代码必需时同步的,因此要想在其中包含异步操作是不合适的。如下代码:

const app = {
    state: {
        //直接访问state中的元素,可获得元素的值,但是不利于封装
        //并且在访问是如果store.count的访问方式也不方便
        //mapStore方便快速将store.count映射到计算属性,但本质上还是直接访问元素的值,无法达到getters封装取值时二次加工的效果
        count: 100
    },
    getters: {
        //对state元素进行取值进行封装,可以方便实现在取值时的各种运算需求
        //mapGetters与mapState类型,实现快速将getters映射到计算属性
        getCount: state => {
            return state.count > 100 ? true : false
        }
    },
    mutations: {
        //对state元素值的写入进行封装,可以方便实现在赋值时的各种运算需求
        //mapMutations与mapState类型,实现快速将mutations映射到方法中methods
        add(state, n) {
            state.count += n
        }
    }
}
export default app

如上面的add中要根据n的奇偶性来异步request不同外部接口获取数据用于运算,此时mutation中就导致无法完成操作。因此在没有actions的概念下,我们只能将(根据n的奇偶性来异步request不同外部接口获取数据)其提前与add执行,然后将执行结果传给add来实现该目的。但这么做的结果是逻辑被拆开,逻辑松散化了。个人认为这就是mutations的短板,为了能将该短板补上,actions就横空出世了。

action中则可以按上面的逻辑执行,并最终提交的mutation add,瞬间海阔天空了!

//基础store配置信息
import Vue from 'vue'

const app = {
    state: {
        //直接访问state中的元素,可获得元素的值,但是不利于封装
        //并且在访问是如果store.count的访问方式也不方便
        //mapStore方便快速将store.count映射到计算属性,但本质上还是直接访问元素的值,无法达到getters封装取值时二次加工的效果
        count: 100
    },
    getters: {
        //对state元素进行取值进行封装,可以方便实现在取值时的各种运算需求
        //mapGetters与mapState类型,实现快速将getters映射到计算属性
        getCount: state => {
            return state.count > 100 ? true : false
        }
    },
    mutations: {
        //对state元素值的写入进行封装,可以方便实现在赋值时的各种运算需求
        //mapMutations与mapState类型,实现快速将mutations映射到方法中methods
        add(state, n) {
            state.count += n
        }
    },
    actions:{
        aadd({commit},n){
            if(n%2){
                Vue.axios.get('http://127.0.0.1:8881/home/a').then(res=>{
                    console.log(res.data)
                    commit('add',res.data)
                })
            }
            else{
                Vue.axios.post('http://127.0.0.1:8881/home/b').then(res=>{
                    console.log(res.data)
                    commit('add',res.data)
                })
            }
        }
    }
}
export default app

这个就能在actions中顺利的执行ajax异步操作了,nice!

完整代码:

//main.js
import Vue from 'vue'
import App from './App.vue'
import Vuex from 'vuex'
import axios from 'axios'
import VueAxios from 'vue-axios'
import storeSetting from './strore'

Vue.use(Vuex)
Vue.use(VueAxios, axios)

const store = new Vuex.Store(storeSetting)

new Vue({
  store,
  render: h => h(App),
}).$mount('#app')
// /store/index.js,基础store配置信息
//引入vue,方便调用axios
import Vue from 'vue'

const app = {
    state: {
        count: 100
    },
    getters: {
        getCount: state => {
            return state.count > 100 ? true : false
        }
    },
    mutations: {
        add(state, n) {
            state.count += n
        }
    },
    actions:{
        aadd({commit},n){
            if(n%2){
                Vue.axios.get('http://127.0.0.1:8881/home/a').then(res=>{
                    console.log(res.data)
                    commit('add',res.data)
                })
            }
            else{
                Vue.axios.post('http://127.0.0.1:8881/home/b').then(res=>{
                    console.log(res.data)
                    commit('add',res.data)
                })
            }
        }
    }
}
export default app
<template>
  <div id="app">
    <p><button @click="add">count</button></p>
  </div>
</template>

<script>
import setting from "./components/routes/nameview/Setting.vue";
import { mapState } from "vuex";

export default {
  components: { setting },
  name: "App",
  methods: {
    add(){
      this.$store.dispatch('aadd',2)
    }
  }
};
</script>

 

posted @ 2020-12-06 12:03  DW039  阅读(928)  评论(0编辑  收藏  举报