Skip to content

Latest commit

 

History

History
77 lines (58 loc) · 2.3 KB

1.md

File metadata and controls

77 lines (58 loc) · 2.3 KB

PureComponent

PureComponent出现,不得不说起React的更新机制,当state或者props变化,React会从根组件从上往下更新渲染,当然有些组件的stateprops变化没有发生变化,也会更新渲染,这样就带来了性能上的问题,因为React在类组件带来了生命周期shouldComponentUpdate函数来组件渲染。

shouldComponentUpdate(nextProps, nextState)

shouldComponentUpdate函数返回true进行更新,返回false组件不进行更新。

PureComponent内部帮组我们实现了,shouldComponentUpdate, props和state的浅对比来实现,代码如下:

if (this._compositeType === CompositeTypes.PureClass) {
  shouldUpdate = !shallowEqual(prevProps, nextProps)
  || !shallowEqual(inst.state, nextState);
}

通过判断当前的propsnextProps 或者statenextState来比较是否更新。

前比较shallowEqual实现如下:

function shallowEqual(objA: mixed, objB: mixed): boolean {
  if (is(objA, objB)) {
    return true;
  }

  if (typeof objA !== 'object' || objA === null ||
      typeof objB !== 'object' || objB === null) {
    return false;
  }

  const keysA = Object.keys(objA);
  const keysB = Object.keys(objB);

  if (keysA.length !== keysB.length) {
    return false;
  }

  // Test for A's keys different from B.
  for (let i = 0; i < keysA.length; i++) {
    if (
      !hasOwnProperty.call(objB, keysA[i]) ||
      !is(objA[keysA[i]], objB[keysA[i]])
    ) {
      return false;
    }
  }

  return true;
}


function is(x: mixed, y: mixed): boolean {
  // SameValue algorithm
  if (x === y) { // Steps 1-5, 7-10
    // Steps 6.b-6.e: +0 != -0
    // Added the nonzero y check to make Flow happy, but it is redundant
    return x !== 0 || y !== 0 || 1 / x === 1 / y;
  } else {
    // Step 6.a: NaN == NaN
    return x !== x && y !== y;
  }
}

判断过程如下:

  1. 通过is函数判断两个值是否相等,is实际上是Object.is的垫片。
  2. 判断两个对象属性keysA.length !== keysB.length长度是否相等。
  3. 如果两个对象的属性长度相等,在进行判断属性的名字是否一样。

PureComponent缺点

可能会因深层的数据不一致而产生错误的否定判断,从而shouldComponentUpdate结果返回false,界面得不到更新。