React - 修正children(下)

React – 修正children(上) 中我提到了React在遍历children过程当中是不允许修正个中的React Element的,这里我要做点补充,就是有个前提是:运用的React黑白紧缩版的,也就是说不是运用react.min.js这类,运用react.min.js则不会报错。

检察React非紧缩版的源码发明,里边有很多如许的代码块,而在紧缩版中是没有的。

if ("development" !== 'production') {
  ......
}

举个例子 React v0.14.4 (解释被我去掉了)

  • react.js

var ReactElement = function (type, key, ref, self, source, owner, props) {
  var element = {
    $$typeof: REACT_ELEMENT_TYPE,
    type: type,
    key: key,
    ref: ref,
    props: props,
    _owner: owner
  };

  if ("development" !== 'production') {
    ......
    Object.freeze(element.props);
    Object.freeze(element);
  }

  return element;
};
  • react.min.js

u = function(e, t, n, r, o, i, u) {
  var s = {
    $$typeof: a,
    type: e,
    key: t,
    ref: n,
    props: u,
    _owner: i
  };
  return s
};

对照紧缩前后,由if (“development” !== ‘production’) {} 包裹的代码块被直接strip掉了,申明紧缩工具确切了得。
这里重点是看紧缩前的,有两行代码很症结:

Object.freeze(element.props);
Object.freeze(element);

检察一下MDN关于Object.freeze的引见:
The Object.freeze() method freezes an object: that is, prevents new properties from being added to it; prevents existing properties from being removed; and prevents existing properties, or their enumerability, configurability, or writability, from being changed. In essence the object is made effectively immutable. The method returns the object being frozen.
意义是说freeze防备了对象被修正,包含增删改属性。倘若在freeze以后修正对象属性,会有两种效果:
1若在非strict mode下,不会报错,然则任何修正都是不起作用的。
2若在strict mode 下,会throw TypeErrors。

看到这里可以晓得,为啥在运用非紧缩版的时刻修正React Element时会提醒报错,恰是由于该对象被freeze了;相反在紧缩版中由于没有freeze,所以可以胜利修正,不会报错。

谈到这里再趁便提下两点:

  • 紧缩时怎样把if (“development” !== ‘production’) {} 去掉的?
    React的README说起到:

To use React in production mode, set the environment variable NODE_ENV to production. A minifier that performs dead-code elimination such as UglifyJS is recommended to completely remove the extra code present in development mode.
晓得UglifyJS的朋侪应当晓得,UglifyJS在紧缩中,假如碰到if的前提是可估计获得的常数效果,那末就会疏忽掉没用的if/else分支。所以 “development” !== ‘production’ 即 false在紧缩时刻就被清算掉了。
UglifyJS细致的紧缩划定规矩引见看这里:解读UglifyJS(四)

  • 为啥在开辟环境下要运用Object.freeze(),引stackoverflow中Sean Vieira的一句话:
    We use Object.freeze to freeze the router and route objects for non-production environments to ensure the immutability of these objects.

在开辟过程当中提醒报错,在线上环境不提醒,有点JAVA编译的滋味,编译时校验信息,提醒正告和毛病,在实行中不校验。
别的,Object.freeze()运转相对较慢,所以线上去掉这个操纵也是为了进步机能。
freeze vs seal vs normal 这个链接有测试的栗子。

总结:开辟过程当中照样用非紧缩版的React好,有利于实时发明问题。
完成!!!

    原文作者:zhoushx3
    原文地址: https://segmentfault.com/a/1190000004402125
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞