快速理解 VUEX 原理
1. vuex 的作用:
vuex其实是集中的数据管理仓库,相当于数据库mongoDB,MySQL等,任何组件都可以存取仓库中的数据。
2. vuex 流程和 vue 类比:
我们看一下一个简单的vue响应式的例子,vue中的 data 、methods、computed,可以实现响应式。
视图通过点击事件,触发 methods 中的 increment 方法,可以更改 data 中 count 的值,一旦 count 值发生变化,computed 中的函数能够把 getCount 更新到视图。
<div id="app"> <button @click="increment"></button> {{getcount}} </app> new Vue({ el: "#app", // state data () { return { count: 0 } }, // actions methods: { increment () { this.count++ } }, // view computed: { getCount(){ return this.count } }, })
(1). 那vuex和这个vue响应式例子有什么关系呢?
我们也可以用vuex来实现同样的功能,来实现vuex与vue的类比。
其实原理都是一样的,在vuex中有四个部分:state 、 mutations 、 actions 、getters
类比:
可以先假设没有 actions的情况下:
他们的对应关系是这样的:
更改数据 mutations->methods
获取数据 getters -> computed
数据 state->data
视图通过点击事件,触发mutations中方法,可以更改state中的数据,一旦state数据发生更改,getters把数据反映到视图。
那么action 又是做什么的呢,可以理解是为了处理异步,而单纯多加的一层。要是没有设计上可以没有这一步。
(2). 那可能很多人有疑问,dispatch,commit,又是做什么的呢?
是时候拿出这张图了:
在 vue 例子中,我们触发的 click 事件,就能触发 methods 中的方法,这是 vue 设计好的。而在 vuex 中则不行了,一定要有个东西来触发才行,就相当于自定义事件 on,emit。vuex 中的 action,mutation 通过 on 自定义的方法,相应的需要 emit 来触发。
他们的关系是这样的: 通过 dispatch 可以触发 actions 中的方法,actions 中的 commit 可以触发 mutations 中的方法。
(3). 我们来看看vuex的示例,来实现vue的同样功能
const store = new Vuex.Store({ state: { count: 0 }, //state的值只能通过mutations来修改 mutations: { increment(state) { state.count++ } }, //this.$store.commit("increment")触发mutations中函数"increment" actions: { increment({commit}) { commit("increment"); //this.$store.commit("increment") } }, //通过getter中的方法来获取state值 getters: { getCount(state) { return state.count } } }) export default store
App.vue
<template> <div id="app"> <button @click="increment">增加</button> {{this.$store.getters.getCount}} </div> </template> <script> export default { methods: { increment(){ //this.$store.dispatch("increment")触发actions函数"increment" this.$store.dispatch("increment") } } } </script>
3. 更改increment函数名-验证对应关系:
通过 dispatch-actions ,commit-mutation 找到了他们之间的连接关系
store.js
const store = new Vuex.Store({ state: { count: 0 }, mutations: { incrementMutations(state) { return state.count++ } }, actions: { incrementActions({commit}) { commit("incrementMutations"); } }, //通过getter中的方法来获取state值 getters: { getCount(state) { return state.count } } }) export default store main.js import Vue from 'vue' import App from './App.vue' import store from './store' Vue.config.productionTip = false new Vue({ store, render: h => h(App) }).$mount('#app')
App.vue
<template> <div id="app"> <div id="app"> <button @click="incrementClick">增加</button> {{this.$store.getters.getCount}} </div> </div> </template> <script> export default { methods: { incrementClick(){ this.$store.dispatch("incrementActions") } } } </script>