前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >vuex学习笔记

vuex学习笔记

作者头像
前端迷
发布2018-10-22 16:03:21
6940
发布2018-10-22 16:03:21
举报
文章被收录于专栏:前端迷前端迷

组件是Vue最强大的功能之一,而组件实例的作用域是相互独立的,意味着不同组件之间的数据是无法相互使用。组件间如何传递数据就显得至关重要,这篇文章主要是介绍Vuex。尽量以通俗易懂的实例讲述这其中的差别,希望对小伙伴有些许帮助。

一、Vuex 是什么?

Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。

二、什么是“状态管理模式”?

一个简单的 Vue 计数应用开始:

代码语言:javascript
复制
new Vue({
  // state
  data () {
    return {
      count: 0
    }
  },
  // view
  template: `
    <div>{{ count }}</div>
  `,
  // actions
  methods: {
    increment () {
      this.count++
    }
  }
})

这个状态自管理应用包含以下几个部分:

state,驱动应用的数据源; view,以声明方式将 state 映射到视图; actions,响应在 view 上的用户输入导致的状态变化。

state 的数据会在 view 上显示出来,用户会根据 view 上的内容进行操作,从而触发 actions,接着再去影响 state(vue 是单向数据流的方式驱动的)。

当我们的应用遇到多个组件共享状态时,单向数据流的简洁性很容易被破坏。下面的图,是把组件的共享状态抽取出来,以一个全局单例模式管理。

三、核心概念

1. state

state:页面状态管理容器对象。集中存储Vue components中data对象的零散数据,以进行统一的状态管理。页面显示所需的数据从该对象中进行读取。

代码语言:javascript
复制
<div>
    {{ $store.state.count }}
  </div>
   console.log(this.$store.state.count)
2. getters

getters:Vuex 允许我们在 store 中定义“getter”(可以认为是 store 的计算属性)。就像计算属性一样,getter 的返回值会根据它的依赖被缓存起来,且只有当它的依赖值发生了改变才会被重新计算。(getters从表面是获得的意思,可以把他看作在获取数据之前进行的一种再编辑,相当于对数据的一个过滤和加工。getters就像计算属性一样,getter 的返回值会根据它的依赖被缓存起来,且只有当它的依赖值发生了改变才会被重新计算。)

定义getter:

代码语言:javascript
复制
getters: {
    done(state) {    
      return state.count + 1;
    },
  }
3. mutations

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

代码语言:javascript
复制
const store = new Vuex.Store({
  state: {
    count: 1
  },
  mutations: {
    increment (state) {
      // 变更状态
      state.count++
    }
  }
})

组件通过commit提交mutations的方式来请求改变state

代码语言:javascript
复制
this.$store.commit('increment')

提交载荷(Payload) mutations方法中是可以传参的,具体用法如下:

代码语言:javascript
复制
mutations: {
    // 提交载荷 Payload
    add(state, n) {
      state.count += n
    }
  },
this.$store.commit('add', 10)
 4.Action

Action:类似于 mutation,不同在于Action 提交的是 mutation,而不是直接变更状态; Action 可以包含任意异步操作。

代码语言:javascript
复制
const store = new Vuex.Store({
  state: {
    count: 0
  },
  mutations: {
    increment (state) {
      state.count++
    }
  },
  actions: {
    increment (context) {
      context.commit('increment')
    }
  }
})

不同于 mutations使用 commit方法, actions使用 dispatch方法。

代码语言:javascript
复制
this.$store.dispatch('incrementAsync')

context context是与 store 实例具有相同方法和属性的对象。可以通过context.state和context.getters来获取 state 和 getters。 以载荷形式分发

代码语言:javascript
复制
incrementAsyncWithValue (context, value) {
  setTimeout(() => {
    context.commit('add', value)
  }, 1000)
}
this.$store.dispatch('incrementAsyncWithValue', 5)
5.Module

由于使用单一状态树,应用的所有状态会集中到一个比较大的对象。当应用变得非常复杂时,store 对象就有可能变得相当臃肿。

为了解决以上问题,Vuex 允许我们将 store 分割成模块(module)。每个模块拥有自己的 state、mutation、action、getter、甚至是嵌套子模块——从上至下进行同样方式的分割:

代码语言:javascript
复制
const moduleA = {
  state: { ... },
  mutations: { ... },
  actions: { ... },
  getters: { ... }
}

const moduleB = {
  state: { ... },
  mutations: { ... },
  actions: { ... }
}

const store = new Vuex.Store({
  modules: {
    a: moduleA,
    b: moduleB
  }
})

store.state.a // -> moduleA 的状态
store.state.b // -> moduleB 的状态

模块的局部状态 对于模块内部的 mutation 和 getter,接收的第一个参数是模块的局部状态对象。

代码语言:javascript
复制
const moduleA = {
  state: { count: 0 },
  mutations: {
    increment (state) {
      // 这里的 `state` 对象是模块的局部状态
      state.count++
    }
  },    
  getters: {
    doubleCount (state) {
      return state.count * 2
    }
  }
}

Vuex计数器的例子: 在src目录下创建一个store文件夹。

store/store.js

代码语言:javascript
复制
import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

const store = new Vuex.Store({
  state: {
    count: 0,
    show: ''
  },
  getters: {
    counts: (state) => {
      return state.count
    }
  },
  mutations: {
    increment: (state) => {
      state.count++
    },
    decrement: (state) => {
      state.count--
    },
    changVal: (state, v) => {
      state.show = v
    }
  }
})
export default store

state就是我们的需要的状态,状态的改变只能通过提交mutations,例如:

代码语言:javascript
复制
increase() {
      this.$store.commit('increment')
    }

带有载荷的提交方式:

代码语言:javascript
复制
changObj () {
      this.$store.commit('changVal', this.obj)
}

载荷也可以是一个对象,这样可以提交多个参数。

代码语言:javascript
复制
changObj () {
      this.$store.commit('changVal', {
          key:''
      })
}

在main.js中引入store.js

代码语言:javascript
复制
import store from './store/store'
export default new Vue({
  el: '#app',
  router,
  store,
  components: {
    App
  },
  template: '<App/>'
})

在组件中使用 在组建可以通过$store.state.count获得状态 更改状态只能以提交mutation的方式。

代码语言:javascript
复制
<div class="store">
  <p>
    {{$store.state.count}}
  </p>
  <button @click="increase"><strong>+</strong></button>
  <button @click="decrease"><strong>-</strong></button>
  <hr>
  <h3>{{$store.state.show}}</h3>
  <input
    placeholder="请输入内容"
    v-model="obj"
    @change="changObj"
    clearable>
  </input>
</div>
</template>
<script>
export default {
  data () {
    return {
      obj: ''
    }
  },
  methods: {
    increase() {
      this.$store.commit('increment')
    },
    decrease() {
      this.$store.commit('decrement')
    },
    changObj () {
      this.$store.commit('changVal', this.obj)
    }
  }
}
</script>
本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2018-10-17,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 前端迷 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 一、Vuex 是什么?
  • 二、什么是“状态管理模式”?
  • 三、核心概念
相关产品与服务
对象存储
对象存储(Cloud Object Storage,COS)是由腾讯云推出的无目录层次结构、无数据格式限制,可容纳海量数据且支持 HTTP/HTTPS 协议访问的分布式存储服务。腾讯云 COS 的存储桶空间无容量上限,无需分区管理,适用于 CDN 数据分发、数据万象处理或大数据计算与分析的数据湖等多种场景。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档