Vuex核心知识整理

news2024/11/24 22:40:30

目录

1 搭建vuex环境

2 求和案例

3 getters 配置项

4 mapState 和 mapGetters

5 mapMutations 和 mapActions

6 Vuex 模块化


1 搭建vuex环境

vuex工作原理图(摘自官网

什么时候使用Vuex:

1.当多个组件依赖于统一状态

2.来自不同组件的行为需要变更同一状态 


(1). 首先再src目录下创建store文件夹,然后创建index.js文件(该文件用于创建 vuex 中最为核心的 store), 然后在main.js中引入这个index.js文件

【index.js】

/* 该文件用于创建 vuex 中最为核心的 store */
// 引入Vue
import Vue from 'vue'

// 引入vuex
import Vuex from 'vuex'

// 使用插件
Vue.use(Vuex)

// 1. 准备actions: 用于响应组件中的动作
const actions = {

    /* 没有业务逻辑的,可以直接跳过这步,直接commit */
    // jia(context, num) {
    //     context.commit('JIA', num)
    // },
    // jian(context, num) {
    //     context.commit('JIAN', num)
    // },

    /* 有业务逻辑的 */
    jiaOdd(context, num) {
        if (context.state.sum % 2) {
            context.commit('JIA', num)
        }
    },
    jiaWait(context, num) {
        setTimeout(() => {
            context.commit('JIA', num)
        }, 1000)
    },
}

// 2. 准备mutations: 用于操作数据(state)
const mutations = {
    JIA(state, num) {
        // console.log(num)
        state.sum += num
    },
    JIAN(state, num) {
        state.sum -= num
    }
}

// 3. 准备state: 用于保存数据
const state = {
    sum: 0,  // 当前的和
}


/* 创建并暴露store */
export default new Vuex.Store({
    actions,
    mutations,
    state
})

2 求和案例

【Count】

<template>
  <div>
    <h1>当前求和为:{{ $store.state.sum }}</h1>
    <select v-model.number="num">
        <option value="1">1</option>
        <option value="2">2</option>
        <option value="3">3</option>
    </select>
    <button @click="add">+</button>
    <button @click="sub">-</button>
    <button @click="addIfOdd">当前求和为奇数再加</button>
    <button @click="addWait">等一等再加</button>
  </div>
</template>

<script>
    export default {
        name: 'Count',
        data() {
            return {
                num: 1, //用户选择的数字
            }
        },
        methods: {
            /* 没有业务处理,直接commit, 联系mutations */
            add() {
                this.$store.commit('JIA', this.num)
            },
            sub() {
                this.$store.commit('JIAN', this.num)
            },

            /* 有业务处理,先dispatch, 联系actions,再commit, 联系mutations */
            addIfOdd() {
                this.$store.dispatch('jiaOdd', this.num) 
            },
            addWait() {
                this.$store.dispatch('jiaWait', this.num)
            }
        },
    }

</script>

<style>
    button {
        margin-left: 8px;
    }
</style>

在组件中使用处理过后的数据时(比如上方的sum ),用 {{ $store.state.sum }} 


3 getters 配置项

【index.js】

......
// 3. 准备state: 用于保存数据
const state = {
    sum: 0,  // 当前的和
    school: '北京大学',
    subject: '计算机'
}

// getters: 用于将state中的数据进行加工
const getters = {
    bigSum(state) {
        return state.sum * 10
    }
}

/* 创建并暴露store */
export default new Vuex.Store({
    actions,
    mutations,
    state,
    getters
})

【Count】

在组件中使用getters中加工后的数据 

<h3>放大十倍的和为:{{ $store.getters.bigSum }}</h3>

4 mapState 和 mapGetters

在上述的案例中,当我们需要使用state或者getters中的数据时,在组件中的模板中,需要写 $store.state.xx, 这样写的话,不够精简。以下将介绍几种方法,利用计算属性去处理这种不足之处

【state和getters中的数据】

// 3. 准备state: 用于保存数据
const state = {
    sum: 0,  // 当前的和
    school: '北京大学',
    subject: '计算机'
}

// 。getters: 用于将state中的数据进行加工
const getters = {
    bigSum(state) {
        return state.sum * 10
    }
}

【在组件中导入】

import { mapState, mapGetters } from 'vuex'

1. 获取state中的数据: 

【方法1】靠程序员自己手写计算属性

.......
computed: {
    /* 1.靠程序员自己去写计算属性 */
    he() {
         return this.$store.state.sum
    },
    xuexiao() {
         return this.$store.state.school
    },
    xueke() {
         return this.$store.state.subject
    },
}

<h1>当前求和为:{{ sum }}</h1>
<h3>我在:{{ xuexiao}}, 学习{{ xueke}}</h3>

【方法2】使用vuex的mapState生成计算属性,从state中获取数据  (对象写法)

computed: {
    // .......


    ...mapState({he:'sum', xuexiao:'school', xueke:'subject'}),  // 使用扩展运算符展开对象
}

【方法3】使用vuex的mapState生成计算属性,从state中获取数据  (数组写法)

computed: {
    // ......

    ...mapState(['sum', 'school', 'subject']),
}

使用数组写法的前提是:计算属性的属性名和state中的数据的名称是相同的


2. 获取getters中的数据: 

【方法1】使用vuex的mapGetters生成计算属性,从getters中获取数据  (对象写法)

computed: {
    // ......

    ...mapGetters({bigSum:'bigSum'})
}

【方法2】使用vuex的mapGetters生成计算属性,从getters中获取数据  (数组写法)

computed: {
    // ......

    ...mapGetters(['bigSum'])
}

前提和上面一样


5 mapMutations 和 mapActions

当我们在组件中想要联系actions 或者 mutations 时,我们需要使用this.$store.dispatch(...) 或者 this.$store.commit(...) 这样写的话,如果有多个就会写很多重复的 this.$store.dispatch ......

所以我们可以使用mapMutations和mapActions来解决这种问题

【在组件中导入】

import { mapMutations, mapActions } from 'vuex'

1. 联系mapMutations:

【方法1】借助vuex的mapMutations生成方法,方法中调用commit方法去联系 mutations (对象的写法)

methods: {
    // ......

    ...mapMutations({add: 'JIA', sub: 'JIAN'}),
}

【方法2】借助vuex的mapMutations生成方法,方法中调用commit方法去联系 mutations (数组的写法)

methods: {
    // .......

    ...mapMutations(['JIA', 'JIAN']),  // 函数名也要改成对应的JIA、JIAN
}

2. 联系mapActions:

【方法1】借助mapActions 对象的写法

methods: {
    // ......
    
    ...mapActions({addIfOdd: 'jiaOdd', addWait: 'jiaWait'})
}

【方法2】借助mapActions 数组的写法

methods: {
    // ......    

    ...mapActions(['addIfOdd', 'addWait'])
}

但是使用上述方法时,并不会传递参数,如果不指定参数的话,会默认传递事件对象 event, 所以计算结果会出错,所以我们需要在 <template></template>中指定传递的参数

    <button @click="add(num)">+</button>
    <button @click="sub(num)">-</button>
    <button @click="addIfOdd(num)">当前求和为奇数再加</button>
    <button @click="addWait(num)">等一等再加</button>

6 Vuex 模块化

【index.js】

/* 该文件用于创建 vuex 中最为核心的 store */
// 引入Vue
import Vue from 'vue'

// 引入vuex
import Vuex from 'vuex'

import axios from 'axios'

import nanoid from 'nanoid'

// 使用插件
Vue.use(Vuex)

/* 1.求和功能相关的配置 */
const countOptions = {
    namespaced: 'true',
    actions: {
        jiaOdd(context, num) {
            if (context.state.sum % 2) {
                context.commit('JIA', num)
            }
        },
        jiaWait(context, num) {
            setTimeout(() => {
                context.commit('JIA', num)
            }, 1000)
        },
    },
    mutations: {
        JIA(state, num) {
            // console.log(num)
            state.sum += num
        },
        JIAN(state, num) {
            state.sum -= num
        },
    
        ADD_PERSON(state, person) {
            state.personList.unshift(person)
        },
    },
    state: {
        sum: 0,  // 当前的和
        school: '北京大学',
        subject: '计算机',
    },
    getters: {
        bigSum(state) {
            return state.sum * 10
        }
    }
}

/* 2.人员功能相关的配置 */
const personOptions = {
    namespaced: 'true',
    actions: {
        addPersonxie(context, person) {
            if (person.name.indexOf('谢') === 0) {
                context.commit('ADD_PERSON', person)
            } else {
                alert('添加的人必须姓谢')
            }
            
        }, 
        addPersonServer(context) {
            axios.get('https://api.uixsj.cn/hitokoto/get?type=social').then(
                response => {
                    context.commit('ADD_PERSON', {id: nanoid(), name: response.data})
                },
                error => {
                    console.log(error.message)
                }
            )
        }
    },
    mutations: {
        ADD_PERSON(state, person) {
            state.personList.unshift(person)
        }
    },
    state: {
        personList: [
            {id:'001', name:'zs'}
        ]
    },
    getters: {
        firstPersonName(state) {
            return state.personList[0].name
        }
    }
}



/* 创建并暴露store */
export default new Vuex.Store({
    modules: {
        count: countOptions,
        person: personOptions
    }
})

使用模块化时,state中就变成了count 和 person两个被导出的模块,而具体的数据就在对应的模块中

在模板中就可以使用以下方式使用数据  {{ count.xx}} 、 {{ person.xx}}

    <h1>当前求和为:{{ count.sum }}</h1>
    <h2>放大十倍的和为:{{ bigSum }}</h2>
    <h3>我在:{{ count.school }}, 学习{{ count.subject }}</h3>

    <h4 style="color: red;">Perosn组件的总人数是: {{ person.personList.length }}</h4>

但是这样写的话,模板中的写法还是过于繁琐,所以我们可以将所需要的数据指定所在的模块中,然后就可以直接用了。

// 这里以对象的写法为例
...mapState('count', ['sum', 'school', 'subject']),  // 需要配置namespaced:true


         methods: {
            ...mapMutations('count', {add: 'JIA', sub: 'JIAN'}),

            ...mapActions('count', {addIfOdd: 'jiaOdd', addWait: 'jiaWait'})

        },

模块化有一个好处就是,可以将每一个模块放入一个.js文件中,然后在store/index.js 文件中引入,这样方便多个程序员根据自己的需要操作对应放入模块

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1452543.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【刷题】牛客— NC21 链表内指定区间反转

链表内指定区间反转 题目描述思路一&#xff08;暴力破解版&#xff09;思路二&#xff08;技巧反转版&#xff09;思路三&#xff08;递归魔法版&#xff09;Thanks♪(&#xff65;ω&#xff65;)&#xff89;谢谢阅读&#xff01;&#xff01;&#xff01;下一篇文章见&…

黑群晖一键修复:root、AME、DTS、转码、CPU型号等

食用方法&#xff1a;SSH连接群晖使用临时root权限执行 AME3.x激活补丁 只适用于x86_64的&#xff1a;DSM7.x Advanced Media Extensions (AME)版本3.0.1-2004、3.1.0-3005 激活过程需要下载官方的解码包&#xff0c;过程较慢&#xff0c;耐心等待。。。 DSM7.1和7.2的AME版…

【开源】SpringBoot框架开发智能教学资源库系统

目录 一、摘要1.1 项目介绍1.2 项目录屏 二、功能模块2.1 数据中心模块2.2 课程档案模块2.3 课程资源模块2.4 课程作业模块2.5 课程评价模块 三、系统设计3.1 用例设计3.2 数据库设计3.2.1 课程档案表3.2.2 课程资源表3.2.3 课程作业表3.2.4 课程评价表 四、系统展示五、核心代…

Vulnhub靶机:DC6

一、介绍 运行环境&#xff1a;Virtualbox 攻击机&#xff1a;kali&#xff08;10.0.2.15&#xff09; 靶机&#xff1a;DC6&#xff08;10.0.2.59&#xff09; 目标&#xff1a;获取靶机root权限和flag 靶机下载地址&#xff1a;https://www.vulnhub.com/entry/dc-6,315/…

基于深度置信网络的多模态过程故障评估方法及应用

源自&#xff1a;自动化学报 作者&#xff1a;张凯, 杨朋澄, 彭开香, 陈志文 “人工智能技术与咨询” 发布 摘 要 传统的多模态过程故障等级评估方法对模态之间的共性特征考虑较少, 导致当被评估模态故障信息不充分时, 评估的准确性较低. 针对此问题, 首先, 提出一种共性–…

springboot登录校验

一、登录功能 二、登录校验 2.1 会话技术 2.2 JWT令牌 JWT令牌解析&#xff1a; 如何校验JWT令牌&#xff1f;Filter和Interceptor两种方式。 2.3 过滤器Filter 2.3.1 快速入门 修改上述代码&#xff1a; 2.3.2 详解 2.3.3 登录校验-Filter 2.4 Interceptor拦截器 2.4.1 …

NLP_Transformer架构

文章目录 Transformer架构剖析编码器-解码器架构各种注意力的应用Transformer中的自注意力Transformer中的多头自注意力Transformer中的编码器-解码器注意力Transformer中的注意力掩码和因果注意力 编码器的输入和位置编码编码器的内部结构编码器的输出和编码器-解码器的连接解…

C++重新认知:智能指针

0/# 一、为什么要有智能指针 内存泄露是我们开发大型项目时最为头疼的问题&#xff0c;当我们将对象建立在堆上时&#xff0c;因为需要我们自己手动释放&#xff0c;因此避免不了忘记删除&#xff0c;或者删除时没有考虑清楚情况的问题&#xff0c;从而造成悬挂指针或者是野指针…

UnityShader——06UnityShader介绍

UnityShader介绍 UnityShader的基础ShaderLab UnityShader属性块介绍 Properties {//和public变量一样会显示在Unity的inspector面板上//_MainTex为变量名&#xff0c;在属性里的变量一般会加下划线&#xff0c;来区分参数变量和临时变量//Texture为变量命名//2D为类型&…

微服务学习Day4

文章目录 初始MQ同步通讯和异步通讯MQ常见技术介绍 RabbitMQ快速入门入门案例 SpringAMQP介绍例子WorkQueue模型exchange交换机消息转换器 初始MQ 同步通讯和异步通讯 MQ常见技术介绍 RabbitMQ快速入门 入门案例 SpringAMQP 介绍 例子 WorkQueue模型 exchange交换机 消息转换…

二进制和进制转换

前言 我们经常能听到2进制、8进制、10进制、16进制这样的讲法&#xff0c;那是什么意思呢&#xff1f;其实2进制、8进 制、10进制、16进制是数值的不同表示形式而已。 比如&#xff1a;数值15的各种进制的表示形式&#xff1a; 15的2进制&#xff1a;111115的8进制&#xff1…

最小生成树(习题)

拆地毯 这个就是套用最小生成树的模板&#xff0c;只不过要将sort函数改成从大到小进行排序。然后这个退出条件是只要大于k就退出。 代码如下 #include<iostream> #include<cmath> #include<algorithm> #define N 1009000 using namespace std; int n,m,k…

HarmonyOS—状态管理概述

在前文的描述中&#xff0c;我们构建的页面多为静态界面。如果希望构建一个动态的、有交互的界面&#xff0c;就需要引入“状态”的概念。 图1 效果图 上面的示例中&#xff0c;用户与应用程序的交互触发了文本状态变更&#xff0c;状态变更引起了UI渲染&#xff0c;UI从“He…

【杂谈】裁我?我是研发,我是研发啊!

闲谈 这两年互联网是越来越不太平了&#xff0c;前有国外互联网裁员的妖风四起&#xff0c;后来寒气又传到国内&#xff0c;让我们这群打工人叫苦连天。最近有部电影蛮火的&#xff0c;叫《年会不能停》&#xff0c;感觉跟我前司很相似&#xff0c;不过好像由于今年业绩不太行…

解决LeetCode编译器报错的技巧:正确处理位操作中的数据类型

一天我在leetcode上刷题时&#xff0c;遇到了这样的题目&#xff1a; 随即我写了如下的代码&#xff1a; int convertInteger(int A, int B) {int count 0;int C A ^ B;int flag 1;while(flag){if (C & flag){count;}flag<<1;}return count;} 但LeetCode显示如下…

you-get,一个超强的 Python 库

你好&#xff0c;我是坚持分享干货的 EarlGrey&#xff0c;翻译出版过《Python编程无师自通》、《Python并行计算手册》等技术书籍。 如果我的分享对你有帮助&#xff0c;请关注我&#xff0c;一起向上进击。 现在在线视频超火爆&#xff0c;可是我还是更倾向于将视频下载至本地…

文件上传漏洞--Upload-labs--Pass03--特殊后缀与::$DATA绕过

方法一&#xff1a;特殊后缀绕过&#xff1a; 一、什么是特殊后缀绕过 源代码中的黑名单禁止一系列后缀名 之外的后缀&#xff0c;称之为‘特殊后缀名’&#xff0c;利用其来绕过黑名单&#xff0c;达到上传含有恶意代码的文件的目的。 二、代码审计 接下来对代码逐条拆解进行…

【IO流】32.IO流

IO流 1. IO流1.1 概述1.2 作用1.3 分类1.4 注意事项 1. IO流 IO流&#xff1a;存储和读取数据的解决方案。 I&#xff1a;input O&#xff1a;output 流&#xff1a;像水流一样传输数据 1.1 概述 IO&#xff08;Input/Output&#xff09;流是计算机程序用于与外部设备进行数据…

CSS之margin塌陷

margin塌陷 CSS中的外边距塌陷&#xff08;Margin Collapse&#xff09;问题是指在垂直方向上&#xff0c;当两个或多个块级元素的边距相遇时&#xff0c;它们之间的距离不是它们各自边距的总和&#xff0c;而是其中的最大值。这种现象主要出现在块级元素的上下外边距之间。 &…

【测试】测试用例篇

目 录 一. 设计测试用例的万能公式(六个)二.设计测试用例的具体方法1.等价类2.边界值3.因果图&#xff08;判定表&#xff09;4.场景设计法5.正交法6.错误猜测法 一. 设计测试用例的万能公式(六个) 设计测试用例的万能公式 测试用例的意义是帮助测试人员了解&#xff1a;测什…