談?wù)剬uex的理解

首先我們先拋出三個問題
(1)有了vuex我們是不是就不需要組件之間傳參?
(2)vuex和localstorage啥區(qū)別?
(3)vuex里面直接修改state為什么還要有專門的修改方法mutation?
先把3個問題的答案放出來:
(1)vuex是多個組件,共享同一個數(shù)據(jù)的狀態(tài)管理工具。只是父子之間的數(shù)據(jù)傳遞沒必要使用vuex,小型項目官方都不推薦使用vuex,只會增加項目的負(fù)擔(dān),大型的項目并且是多個組件共享的用vuex更好
(2)vuex和localstorage兩者應(yīng)用場景不同。vuex是當(dāng)前vue項目的全局狀態(tài)對象,存放在內(nèi)存中,一旦當(dāng)前vue項目刷新,vuex的數(shù)據(jù)也將恢復(fù)默認(rèn)值;而localstorage是存放在瀏覽器中的對象,即使刷新數(shù)據(jù)也仍然存在。
(3)對于這個問題,在創(chuàng)建 store 的時候傳入 strict: true, 開啟嚴(yán)格模式,那么任何修改state的操作,只要不經(jīng)過mutation的函數(shù),vue就會 throw error

const store = new Vuex.Store({
   state,
   strict:true
   //開啟嚴(yán)格模式后,只能通過mutation來改變狀態(tài)(不支持異步)否則會報錯
})
//下面的開啟嚴(yán)格模式就會報錯,不開啟是可行的
  console.log(store.state.count) //0
  store.state.count = 3;
  console.log(store.state.count)  //3

注意:發(fā)布環(huán)境下不要開啟嚴(yán)格模式,嚴(yán)格模式會深度監(jiān)測狀態(tài)樹來檢測不合規(guī)的狀態(tài)變化,造成不必要的性能損失
但是真正原因是:
Vuex的state是響應(yīng)式的,響應(yīng)式就是狀態(tài)改變頁面組件也實時更新。但是要實現(xiàn)響應(yīng)式必須通過提交mutation去改變state,并且還需要遵守一定的規(guī)則

image.png

下面從是什么,為什么,怎么用的角度來談對vuex的理解

【1】vuex是什么

多個組件,共享,同一個數(shù)據(jù)的狀態(tài)管理工具
vuex適用于大型單頁應(yīng)用,簡單的應(yīng)用使用 Vuex 可能是繁瑣冗余的

【2】為什么

當(dāng)在開發(fā)大型單頁應(yīng)用時,會出現(xiàn)多個視圖組件依賴同一個狀態(tài),來自不同視圖的行為需要變更同一個狀態(tài)。如登錄狀態(tài)、加入購物車、音樂播放等。
或許你認(rèn)為可以用傳參的方法解決組件之間互相傳值的問題。但是傳參的方法對于多層嵌套的組件將會變得很繁瑣,并且對于兄弟組件間的傳遞無能為力。所以vuex出現(xiàn)了,相當(dāng)于一個“前端的數(shù)據(jù)庫”。
Vuex主要用于解決組件之間同一狀態(tài)的共享問題,它能把組件的共享狀態(tài)抽取出來,當(dāng)做一個全局單例模式進(jìn)行管理。 這樣不管你在何處改變狀態(tài),都會通知使用該狀態(tài)的組件做出相應(yīng)修改。即Vuex采用集中式存儲管理應(yīng)用的所有組件的狀態(tài) 這里的關(guān)鍵在于集中式存儲管理。 這意味著本來需要共享狀態(tài)的更新是需要組件之間的通訊,而現(xiàn)在有了Vuex,組件就都和store通訊了

【3】怎么用

安裝使用步驟
1.安裝
sudo cnpm install vuex -S
2.引入狀態(tài)管理工具vuex
import vuex from 'vuex'
import store from './vuex/store'
3.main.js里面實例化
new Vue({
  el: '#app',
  router, :style="{ 'left': leftnum + 'px' }"  
  store,
  components: { App },
  template: '<App/>'
})
4.在src里面和views同級創(chuàng)建vuex文件里面store.js
import Vue from 'vue'
import Vuex from 'vuex'
Vue.use(Vuex)
const store = new Vuex.Store({
  // 定義狀態(tài)
  state: {
    //動態(tài)路由的數(shù)組
    keepAlive:[],
    //全局域名
    domainName:"",
  }
})
export default store

5.使用:this.$store.state.名字

使用方法核心內(nèi)容

(1)state 存放狀態(tài)
(2)mutations 美[mju??tion] 同步的,唯一更改state的方法是提交 mutation。
(3)getters 加工state成員給外界類似于計算屬性
(4)actions 異步的,然后提交mutation去操作state
(5)modules 模塊化狀態(tài)管理


image.png
(1)state 存放狀態(tài)
const store = new Vuex.store({
    state:{
        name:'jack'
    },
})
//頁面調(diào)用
this.$store.state
(2)mutations同步的對state操作的集合,比如對該數(shù)據(jù)的修改、增加、刪除等等。里面的函數(shù)有兩個默認(rèn)形參([state] [payload])

state是當(dāng)前VueX對象中的state
payload是該方法在被調(diào)用時傳遞參數(shù)使用的

//index.js
import Vue from 'vue'
import Vuex from 'vuex'
Vue.use(Vuex)
const store = new Vuex.store({
    state:{
        name:'jack'
    },
    mutations:{
        //es6語法,等同edit:funcion(){...}
        //編輯
        edit(state,payload){
            //(1)直接調(diào)用
            state.name = 'wayne'
            //(2)傳值調(diào)用
            state.name = payload
            //(3)傳值對象調(diào)用
            state.name = payload.name
        },
        //新增
        myadd(state,payload){
            //新增邏輯
            Vue.set(state,"name1","dawei")
        },
        //刪除  
        mydel(state,payload){
            //刪除邏輯
            Vue.delete(state,"name1")
        },
    }
})
export default store
//頁面通過this.$store.commit調(diào)用
//(1)直接調(diào)用
this.$store.commit('edit')
//(2)傳值調(diào)用
this.$store.commit('edit','wayne')
//(3)傳值對象調(diào)用
this.$store.commit('edit',{name:'wayne',sex:'男'})
//還可以這么寫
this.$store.commit({
    type:'edit',
    payload:{
        name:'wayne',
        sex:'男'
    }
})
image.png

新增和刪除不能使用xx.xx = xx,delete state.info.age這種原來的模式因為不是響應(yīng)式的,響應(yīng)式規(guī)定新增和刪除有自己的方法,這樣才能自動更新到組件上面去;
新增用Vue.set(state,"name1","dawei"),
刪除用Vue.delete(state,"name1")

(3)getters 加工state成員給外界類似于計算屬性

可以對state中的成員加工后傳遞給外界,Getters中的方法有兩個默認(rèn)參數(shù)
state 當(dāng)前VueX對象中的狀態(tài)對象
getters 當(dāng)前getters對象

//index.js
import Vue from 'vue'
import Vuex from 'vuex'
Vue.use(Vuex)
const store = new Vuex.store({
    state:{
        name:'jack',
        age:'15'
    },
    mutations:{
        //編輯
        edit(state,payload){
        }
    },
    getters:{
       nameInfo(state){
           return "姓名:"+state.name
       },
       fullInfo(state,getters){
           return getters.nameInfo+'年齡:'+state.age
        }  
  }
})
export default store
// 調(diào)用
this.$store.getters.fullInfo//姓名:jack 年齡:15
(4)actions 專門放置異步操作,然后提交mutation去操作state

注意:Action 提交的是 mutation,而不是直接改變state,只有mutation能改變state。
至于是在頁面組件中等異步操作(如axious請求接口改變state)完成后去commit調(diào)用mutation;還是直接action去做異步axious,根據(jù)不同的業(yè)務(wù)場景有不同的選擇,也有不同的好處體現(xiàn)出來。
比如多次遇到的異步(如axious請求接口改變state)那就直接放在action里面,需要的時候頁面組件直接使用this.$store.dispatch就可以不用重復(fù)寫axious,所以vuex只是為了更靈活使開發(fā)者多一個選擇,讓代碼盡可能的變動優(yōu)雅。
Actions中的方法有兩個默認(rèn)參數(shù)
context 上下文(相當(dāng)于箭頭函數(shù)中的this)對象
payload 掛載參數(shù)

//index.js
import Vue from 'vue'
import Vuex from 'vuex'
Vue.use(Vuex)
const store = new Vuex.store({
    state:{
        name:'jack'
    },
    mutations:{
        //es6語法,等同edit:funcion(){...}
        //編輯
        edit(state,payload){
            //(2)傳值調(diào)用
            state.name = payload
        }
    },
    actions:{
        Edit(context,payload){
            //異步操作
            setTimeout(()=>{
                //提交mutations方法,修改state
                context.commit('edit',payload)
            },2000)
        }
      }
})
export default store

//在頁面組件中調(diào)用:
this.$store.dispatch('Edit','wayne')
(5)modules 模塊化狀態(tài)管理

當(dāng)項目龐大,狀態(tài)非常多時,可以采用模塊化管理模式。Vuex 允許我們將 store 分割成模塊(module)。每個模塊擁有自己的 state、mutation、action、getter、甚至是嵌套子模塊——從上至下進(jìn)行同樣方式的分割。

const store = new Vuex.Store({
models:{
    a:{
        state:{},
        getters:{},
        ....
    },
     b:{
        state:{},
        getters:{},
        ....
    },
}
})
//調(diào)用
this.$store.state.a
//而提交或者dispatch某個方法和以前一樣,會自動執(zhí)行所有模塊內(nèi)的對應(yīng)type的方法:
this.$store.commit('editKey')
this.$store.dispatch('aEditKey')
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • Vuex五個概念的簡單理解。 1.State 保存共享狀態(tài)信息的地方。2.Getters 類似我們單個組件中的計算...
    似朝朝我心閱讀 981評論 0 6
  • 為什么需要Vuex 通常 Vue 項目中的數(shù)據(jù)通信,我們通過以下三種方式就可以解決,但是隨著項目多層嵌套的組件增加...
    尤小小閱讀 1,195評論 1 5
  • vuex是什么 Vuex 是一個專為 Vue.js 應(yīng)用程序開發(fā)的狀態(tài)管理模式。它采用集中式存儲管理應(yīng)用的所有組件...
    為光pig閱讀 302評論 0 0
  • 久違的晴天,家長會。 家長大會開好到教室時,離放學(xué)已經(jīng)沒多少時間了。班主任說已經(jīng)安排了三個家長分享經(jīng)驗。 放學(xué)鈴聲...
    飄雪兒5閱讀 7,868評論 16 22
  • 今天感恩節(jié)哎,感謝一直在我身邊的親朋好友。感恩相遇!感恩不離不棄。 中午開了第一次的黨會,身份的轉(zhuǎn)變要...
    余生動聽閱讀 10,918評論 0 11

友情鏈接更多精彩內(nèi)容