为什么用immutable.js呢。有了immutable.js可以大大提升react的性能。

JavaScript 中的对象一般是可变的(Mutable),因为使用了引用赋值,新的对象简单的引用了原始对象,改变新的对象将影响到原始对象。如 foo={a: 1}; bar=foo; bar.a=2 你会发现此时 foo.a 也被改成了 2。虽然这样做可以节约内存,但当应用复杂后,这就造成了非常大的隐患,Mutable 带来的优点变得得不偿失。为了解决这个问题,一般的做法是使用 shallowCopy(浅拷贝)或 deepCopy(深拷贝)来避免被修改,但这样做造成了 CPU 和内存的浪费。

而Immutable Data 就是一旦创建,就不能再被更改的数据。对 Immutable 对象的任何修改或添加删除操作都会返回一个新的 Immutable 对象。Immutable 实现的原理是 Persistent Data Structure(持久化数据结构),也就是使用旧数据创建新数据时,要保证旧数据同时可用且不变。同时为了避免 deepCopy 把所有节点都复制一遍带来的性能损耗,Immutable 使用了 Structural Sharing(结构共享),即如果对象树中一个节点发生变化,只修改这个节点和受它影响的父节点,其它节点则进行共享

当state更新时,如果数据没变,也会去做virtual dom的diff,这就产生了浪费。而immutable能优化diff算法的性能。

  • Immmutable collection被当做值对待,而不是对象
  • 任何修改会返回新的immutable collection
  • 几乎所有的Array方法均可用在Immutable.List;几乎所有的Map方法均可用在Immutable.Map;几乎所有的Set方法均可用在Immutable.Set
// 使用Immutable
foo = Immutable.fromJS({a: {b: 1}}); //js对象转成Immutable对象 相反toJs()
bar = foo.setIn(['a', 'b'], 2); // 深层使用 setIn 赋值
console.log(foo.getIn(['a', 'b'])); // 使用 getIn 取值,打印 1
console.log(foo === bar); // 打印 false
  • 如果js对象想map遍历,可以利用Immutable的Seq高效实现。 
    Seq只执行需要的工作,不会创建Immuntable缓存数组。任何数据可以通过toSeq()转换为lasy Seq格式
var myObject = {a:1,b:2,c:3};
Immutable.Seq(myObject).map(x => x * x).toObject();
// { a: 1, b: 4, c: 9 }
  • Immutable的Map对象和原生js对象可以无痛合并
// 合并merge
var map1 = Immutable.Map({a:1, b:2, c:3, d:4});
var map2 = Immutable.Map({c:10, a:20, t:30});
var obj = {d:100, o:200, g:300};
console.log(map1.merge(map2, obj).toJS()); // Map{}

// Map
  var obj1 = Immutable.Map({a:1, b:2, c:3});
  var obj2 = obj1.set('b', 50); // set
  console.log(obj1.get('b'),obj2.get('b')); // get 2 50
  var alpha = Immutable.Map({a:1, b:2, c:3, d:4});
  console.log(alpha.map((v, k) => k.toUpperCase()).join());// 'A,B,C,D'

// List
  const list = Immutable.List([ 'a', 'b', 'c' ])
  const result = list.update(2, val => val.toUpperCase())
  console.log("===>",result.toJS())


  • js对象转换为Immutable时,属性都是String类型的。而Immutable.Map接受任何类型,所以get方法不建议使用
var map = Immutable.fromJS(obj);
map.get("1"); // "one"
map.get(1); // undefined
  • 针对嵌套数据的处理方法,mergeDeep/getIn/setIn/updateIn是最常用的方法。
var nested2 = nested.mergeDeep({a:{b:{d:6}}});
// Map { a: Map { b: Map { c: List [ 3, 4, 5 ], d: 6 } } }
nested2.getIn(['a', 'b', 'd']); // var nested3 = nested2.updateIn(['a', 'b', 'd'], value => value + 1);
// Map { a: Map { b: Map { c: List [ 3, 4, 5 ], d: 7 } } } var nested4 = nested3.updateIn(['a', 'b', 'c'], list => list.push(6));
// Map { a: Map { b: Map { c: List [ 3, 4, 5, 6 ], d: 7 } } }

react中使用immutable

  getInitialState() {
return {
data: Map({ times: 0 })
}
},
handleAdd() {
this.setState({ data: this.state.data.update('times', v => v + 1) });
// 这时的 times 并不会改变
console.log(this.state.data.get('times'));
}

immutable+flux

this.state={
searcnfinanceTypeListAll: Immutable.fromJS([])
} changeState=()=>{
this.setState({searcnfinanceTypeListAll:Immutable.fromJS(typeList)});
}

建议把 this.state 写成 Immutable 对象

Immutable学习及 React 中的实践的更多相关文章

  1. [转] Immutable 详解及 React 中实践

    https://zhuanlan.zhihu.com/p/20295971 作者:camsong链接:https://zhuanlan.zhihu.com/p/20295971来源:知乎著作权归作者所 ...

  2. Immutable 详解及 React 中实践

    本文转自:https://github.com/camsong/blog/issues/3 Shared mutable state is the root of all evil(共享的可变状态是万 ...

  3. immutable.js 在React、Redux中的实践以及常用API简介

    immutable.js 在React.Redux中的实践以及常用API简介 学习下 这个immutable Data 是什么鬼,有什么优点,好处等等 mark :  https://yq.aliyu ...

  4. Immutable.js 以及在 react+redux 项目中的实践

    来自一位美团大牛的分享,相信可以帮助到你. 原文链接:https://juejin.im/post/5948985ea0bb9f006bed7472?utm_source=tuicool&ut ...

  5. [转] React之Immutable学习记录

    从问题说起:熟悉 React 组件生命周期的话都知道:调用 setState 方法总是会触发 render 方法从而进行 vdom re-render 相关逻辑,哪怕实际上你没有更改到 Compone ...

  6. 转 : CSS Modules详解及React中实践

    https://zhuanlan.zhihu.com/p/20495964 CSS 是前端领域中进化最慢的一块.由于 ES2015/2016 的快速普及和 Babel/Webpack 等工具的迅猛发展 ...

  7. React 与 Redux 在生产环境中的实践总结

    React 与 Redux 在生产环境中的实践总结 前段时间使用 React 与 Redux 重构了我们360netlab 的 开放数据平台.现将其中一些技术实践经验总结如下: Universal 渲 ...

  8. react中为什么要使用immutable

    因为在react中,react的生命周期中的setState()之后的shouldComponentUpdate()阶段默认返回true,所以会造成本组件和子组件的多余的render,重新生成virt ...

  9. TypeScript在react项目中的实践

    前段时间有写过一个TypeScript在node项目中的实践. 在里边有解释了为什么要使用TS,以及在Node中的一个项目结构是怎样的. 但是那仅仅是一个纯接口项目,碰巧赶上近期的另一个项目重构也由我 ...

随机推荐

  1. SPOJ QTREE Query on a tree ——树链剖分 线段树

    [题目分析] 垃圾vjudge又挂了. 树链剖分裸题. 垃圾spoj,交了好几次,基本没改动却过了. [代码](自带常数,是别人的2倍左右) #include <cstdio> #incl ...

  2. K-D tree入门

    久仰K-D tree大名已久,终于在合适的时候遇见了合适的水题入了坑入了门 K-D tree是什么 K-D tree是什么? 按名字上翻译来就是K维的树,就是一个用来维护K维空间的点的平衡二叉树 K- ...

  3. 常州模拟赛d4t1 立方体

    题目描述 立方体有 6 个面,每个面上有一只奶牛,每只奶牛都有一些干草.为了训练奶牛的合作精神,它 们在玩一个游戏,每轮:所有奶牛将自己的干草分成 4 等份,分给相邻的 4 个面上的奶牛. 游戏开始, ...

  4. 洛谷 P 3371 单元最短路

    题目描述 如题,给出一个有向图,请输出从某一点出发到所有点的最短路径长度. 输入输出格式 输入格式: 第一行包含三个整数N.M.S,分别表示点的个数.有向边的个数.出发点的编号. 接下来M行每行包含三 ...

  5. *hdu5632Rikka with Array

    $n \leq 10^300$,问所有$i<j$且$f_i>f_j$的$(i,j),1 \leq i \leq n,1 \leq j \leq n$数量.对某个数取模. $f(a,b,0/ ...

  6. Android 网络编程之HttpURLConnection运用

    Android 网络编程之HttpURLConnection 利用HttpURLConnection对象,我们可以从网络中获取网页数据. 01 URL url = new URL("http ...

  7. iOS7坐标上移44pt的解决

    在iOS7中,引入一个新的属性,叫[UIViewController setEdgesForExtendedLayout:],它的默认值是UIRectEdgeAll.当容器为UINavigationC ...

  8. Scrapy学习-9-FromRequest

    用FromRequest模拟登陆知乎网站 实例 默认登陆成功以后的请求都会带上cookie # -*- coding: utf-8 -*- import re import json import d ...

  9. Linux下二进制包、源代码包、rpm包

    主要提供三种格式的mysql包:rpm格式.二进制格式.源码格式:(tar打包,gz压缩) rpm格式: libjpeg-devel-6b-33.x86_64.rpm       #rpm格式很好区分 ...

  10. BUPT复试专题—奇偶求和(2014软件)

    题目描述 给出N个数,求出这N个数,奇数的和以及偶数的和. 输入 第一行为测试数据的组数T(1<=T<=50).请注意,任意两组测试数据之间是相互独立的. 每组数据包括两行: 第一行为一个 ...