immot v0.3.4
immot
在不改变原始数据的情况下,创建新的拷贝。
安装
pnpm i immot或者
yarn add immot介绍
不可变数据 是函数式编程中极其重要的一个基本概念。React 的 state 设计为只读,即 不可变数据,只能通过 setState 修改。此模块可以完美配合 React,以简化 setState 操作不可变数据的繁琐步骤。
在 React 中,你不能这样做:
state.a.b.c = 1;
// or...
state.c.d.f.push(2);通常,你会这样做:
const nextState = {
...state,
a: {
...state.a,
b: {
...state.a.b,
c: 1,
},
},
};现在有了 immot,让操作深层数据变得简单:
const nextState = $setIn(state, ['a', 'b', 'c'], 1);
nextState === state;
// false注意 immot 不是深拷贝,深拷贝操作极其昂贵,无法适用于日常开发。immot 只会创建改变的数据,会引用原对象中未改变的部分。
immot 的 API 灵感来自于 immutable-js,但 immutable-js 有独立的结构模型,复杂度高。immot 的设计理念是要求简单、易用,不需要过多的心智负担。因此在设计之初就亲和原生的 JSON 结构,只提供辅助函数,大小 < 1KB,就做到像 immutable-js 一样的效果。
immot 做到了 typescript 类型安全。$updateIn、$setIn、$mergeIn 中的 keyPath 路径支持类型自动提示(目前只支持小于 7 层结构)。

使用
import * as immot from 'immot';或者只导入其中某个函数
import { $updateIn } from 'immot';immot 所有函数操作都会返回一个新的对象。
$set
用于设置 对象/数组/Map 中的属性值。keyPath 为字符串。
const result = immot.$set(demo, 'a', 1);$setIn
用于设置 对象/数组/Map 中的属性值。它可以为深层对象做操作,keyPath 为路径数组
const result = immot.$setIn(demo, ['a', 'b', 1, 'c'], 'good');$merge
用于合并 对象/数组 中的属性列表。
const result = immot.$merge(demo, { tom: 1, jack: 2 });
const result1 = immot.$merge(demo1, [5, 6]);$mergeIn
用于合并 对象/数组 中的属性列表。它可以为深层对象做操作,keyPath 为路径数组
const result = immot.$mergeIn(demo, ['a', 1, 'b'], { tom: 1, jack: 2 });$update
通过回调函数设置 对象/数组/Map 中的属性值。keyPath 为字符串。
const result = immot.$update(demo, 'money', (prev) => prev + 1);$updateIn
通过回调函数设置 对象/数组/Map 中的属性值。它可以为深层对象做操作,keyPath 为路径数组
const result = immot.$updateIn(demo, ['todoList', 0, 'complete'], (complete) => !complete);$delete
用于删除 对象/数组/Map 中的可选属性值,keyPath 为字符串或者数组
const result = immot.$delete(demo, 'a1');
const result1 = immot.$delete(demo, ['a1', 'a2']);$push
类似 Array.prototype.push,但返回新数组
const result = immot.$push(demo, 4);$pop
类似 Array.prototype.pop,但返回新数组
const result = immot.$pop(demo);$shift
类似 Array.prototype.shift,但返回新数组
const result = immot.$shift(demo);$unshift
类似 Array.prototype.unshift,但返回新数组
const result = immot.$unshift(demo, 4);$splice
类似 Array.prototype.splice,但返回新数组
const result = immot.$splice(demo, 1, 0, 'test');性能测试
在 /bench 目录中有性能测试对比的样例,可以 clone 本项目测试
cd bench
pnpm i
node index.mjs注意:
- 数值为每秒操作数量,越高越好
- 样例中
immer关闭了自动冻结对象的特性,否则结果会更差。 - 数组性能测试图中隐藏了
immutableJS数据,用空间换取时间的方式导致数值太高,影响对比。
在 Node v14.17.0 的测试结果:
常规数据和深层数据

50000 长度的数组
