mobx基本使用

本文介绍了MobX的基本概念,包括状态(state)、衍生(derivations)和动作(actions)。MobX支持单向数据流,状态改变会自动更新受影响的视图。文章详细阐述了工作流程,如actions改变state,computed values和reactions根据state自动更新。还探讨了observable、computed、action、autorun等核心API的使用,并提供了实例说明。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

mobx是一个简单可扩展的状态管理库

基本概念
  1. state(状态) 状态是驱动应用的数据,像有数据的excel表格

2.derivations(衍生) 任何源自状态并且不会再进一步相互作用的东西。比如用户界面,待办事件的数量,把变化发送到服务端

两种类型的衍生

(1)computed values 是可以使用pure function从state中推导的值,mobx可以自动更新,并且在不在使用时将其优化掉,比如

@computed get completedTodos(){
    return this.todos.filter(todo => todo.done)
}

(2)reactions很像computed values,会对state的变化做出反应,例如更新UI

const Todos = observer({todos} =>
    <ul>
        todos.map( todo =>
            <li>{todo.title}</li>
        )
    </ul>
)

3.actions动作 动作 是任一一段可以改变状态的代码。用户事件、后端数据推送、预定事件、等等。 动作类似于用户在excel单元格中输入一个新的值。

actions可以改变state,并且是唯一改变state的东西

原则
MobX 支持单向数据流,也就是动作改变状态,而状态的改变会更新所有受影响的视图。

当状态改变时,所有衍生都会进行原子级的自动更新,不能观测到中间值。

所有衍生默认的都是同步更新。动作可以在改变状态之后直接安全的检查计算值???

计算值是延迟更新的,不使用的计算值不更新,直到使用时。

所有的计算值都是纯净的,不应该用来改变state


mobx工作流程



事件调用actions,actions可以改变state,并且唯一能改变state的就是action

@action onClick = () => {
    this.props.todo.done = true;
}

state是可观察的,并且不包含冗余的数据

@observable todos = [{
    title: 'learn mobx',
    done: false
}]

computed values 是可以使用pure function从state中推导的值,mobx可以自动更新,并且在不在使用时将其优化掉

@computed get completedTodos(){
    return this.todos.filter(todo => todo.done)
}

reactions很像computed values,会对state的变化做出反应,例如更新UI

const Todos = observer({todos} =>
    <ul>
        todos.map( todo =>
            <li>{todo.title}</li>
        )
    </ul>
)
一个例子

1.定义状态并使其可观察

所有改变的属性打上,mobx的标记使其变得可观察。

import {observable} from 'mobx';

var appState = observable({
    timer:0
});

2.创建视图以响应状态的变化

创建视图,在appState中相关数据发生改变时视图会自动更新。

import {observer} from 'mobx-react';
@observer
class TimerView extends React.Component{
    render(){
        return (<button onClick={this.onReset.bind(this)}>  
        Seconds passed: {this.props.appState.timer}</button>);
    }
    onReset () {
        this.props.appState.resetTimer();
    }
};

ReactDOM.render(<TimerView appState={appState} />,document.body);

定义一个按钮,显示timer,当点击这个按钮时,调用reset函数,重置时间。

3.更改状态

每秒都修改数据,当需要的时候UI自动更新

appState.resetTimer = action(function reset(){
    appState.timer = 0;
});

setInterval(action(function tick(){
    appState.timer +=1;
}),1000);
API

1.observable 用法:

--observable(value)
--@observable classProperty = value

Observable 值可以是JS基本数据类型、引用类型、普通对象、类实例、数组和映射

const list = observable([1, 2, 4]);
list[2] = 3;

@observable装饰器可以在 ES7 或者 TypeScript 类属性中属性使用,将其转换成可观察的。

import { observable, computed } from "mobx";

class OrderLine {
    @observable price = 0;
    @observable amount = 1;

    @computed get total() {
        return this.price * this.amount;
    }
}

2.computed

计算值(computed values)是可以根据现有的状态或其它计算值衍生出的值。计算值还是高度优化过的,所以尽可能的多使用它们。

import {observable, computed} from "mobx";

class OrderLine {
    @observable price = 0;
    @observable amount = 1;

    constructor(price) {
        this.price = price;
    }

    @computed get total() {
        return this.price * this.amount;
    }
}
计算值的 setter

还可以为计算值定义 setter。注意这些 setters 不能用来直接改变计算属性的值,但是它们可以用来作“逆向”衍生。

注意永远在 getter 之后 定义 setter
class Foo {
    @observable length = 2;
    @computed get squared() {
        return this.length * this.length;
    }
    set squared(value) { // 这是一个自动的动作,不需要注解
        this.length = Math.sqrt(value);
    }
}

(暂时没有用到过,不知道用来干什么需要使用)

3.autorun

当你需要从反应式代码桥接到命令式代码的情况,例如打印日志、持久化或者更新UI的代码,应该使用autorun

当使用 autorun 时,所提供的函数总是立即被触发一次,然后每次它的依赖关系改变时会再次被触发

var numbers = observable([1,2,3]);
var sum = computed(() => numbers.reduce((a, b) => a + b, 0));

var disposer = autorun(() => console.log(sum.get()));
// 输出 '6'
numbers.push(4);
// 输出 '10'
  1. action

动作是任何用来修改状态的东西

action.bound 来自动地将动作绑定到目标对象

class Ticker {
    @observable tick = 0

    @action.bound
    increment() {
        this.tick++ // 'this' 永远都是正确的
    }
}

const ticker = new Ticker()
setInterval(ticker.increment, 1000)
注意: action.bound 不要和箭头函数一起使用;箭头函数已经是绑定过的并且不能重新绑定。
runInAction

runInAction 是个简单的工具函数,它接收代码块并在(异步的)动作中执行。这对于即时创建和执行动作非常有用,例如在异步过程中。

如果你使用async function来处理业务,需要使用runInAction。

computed 和 autorun

它们都是响应式调用的表达式,但是,如果你想响应式的产生一个可以被其它 observer 使用的值,请使用 @computed.

使用 autorun达到某种效果,比如像打印日志、发起网络请求等



React-Mobx是React应用程序和Mobx状态管理库的结合。它帮助开发人员在应用程序中轻松管理和更新状态,同时提高应用程序的性能。 下面是使用React-Mobx基本步骤: 1. 安装React-Mobx使用npm安装React-Mobx库。 ``` npm install mobx mobx-react --save ``` 2. 创建一个store:一个store是包含应用程序状态的对象。它可以包含数据和方法,用于更新和管理状态。 ```javascript import { observable, action } from 'mobx'; class CounterStore { @observable count = 0; @action increment() { this.count++; } @action decrement() { this.count--; } } const counterStore = new CounterStore(); export default counterStore; ``` 3. 在React组件中使用store:使用`Provider`组件将store传递给React组件,然后使用`inject`和`observer`高阶组件包装组件。 ```javascript import React from 'react'; import { Provider, inject, observer } from 'mobx-react'; import counterStore from './counterStore'; @inject('counterStore') @observer class Counter extends React.Component { render() { const { counterStore } = this.props; return ( <div> <h1>Count: {counterStore.count}</h1> <button onClick={counterStore.increment}>+</button> <button onClick={counterStore.decrement}>-</button> </div> ); } } const App = () => ( <Provider counterStore={counterStore}> <Counter /> </Provider> ); export default App; ``` 在这个例子中,`inject`高阶组件将store作为props传递给`Counter`组件,`observer`高阶组件将组件转换为响应式组件,使组件能够响应store中状态的更改。 4. 更新状态:使用store中的方法更新状态。 ```javascript import counterStore from './counterStore'; counterStore.increment(); counterStore.decrement(); ``` 这些是使用React-Mobx基本步骤。使用React-Mobx可以更轻松地管理和更新状态,同时提高应用程序的性能。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值