代码之家  ›  专栏  ›  技术社区  ›  Yuji 'Tomita' Tomita

React忽略浅层比较中的一个属性,或访问默认React shallowCompare for反应备忘录

  •  1
  • Yuji 'Tomita' Tomita  · 技术社区  · 6 年前

    我想让一个组件中的一个prop是一个字符串数组,可以进行深度比较: <ChildComponent deepCompareThis={['a', 'b']} /> 所以我想把它从浅层比较中删除,因为这个数组总是会在浅层比较中失败。为了便于阅读,我想保留这个语法。我使用的是函数组件,所以使用 React.memo .

    反应备忘录 并深入比较一个道具,同时回落到反应自己的违约 https://github.com/facebook/react/blob/master/packages/shared/shallowEqual.js 其他的一切。

    编辑:看浅比较,似乎只要你用 Object.is 对于其他props值,应该具有相同的比较函数。也许复制比较函数并不像我想象的那么可怕。大部分是优化!

    0 回复  |  直到 6 年前
        1
  •  1
  •   95faf8e76605e973    6 年前

    下面是我的解决方案:(1)对于您尝试进行深度比较的道具,您可以为其编写单独的逻辑;(2)对于其余的道具,使用React已经为浅层比较编写的相同逻辑。请看下面我的源代码以及其中的注释,以了解更多信息

    const CustomComponent = React.memo(
      (props) => {
        React.useEffect(() => {
          console.log("CustomComponent render");
        });
    
        return "";
      },
      (prevProps, nextProps) => {
        // destructure the prop you want to specifically target for deep comparison
        // the rest will be shallow compared
        const { deepCompareThis: prevDeep, ...prevRest } = prevProps;
        const { deepCompareThis: nextDeep, ...nextRest } = nextProps;
    
        // your custom logic for the deep comparison
        // i took this function from https://stackoverflow.com/a/16436975/8680805
        function arraysEqual(a, b) {
          if (a === b) return true;
          if (a == null || b == null) return false;
          if (a.length !== b.length) return false;
    
          for (var i = 0; i < a.length; ++i) {
            if (a[i] !== b[i]) return false;
          }
          return true;
        }
    
        const deep_comparison_result = arraysEqual(prevDeep, nextDeep);
        console.log(`deep comparison`, deep_comparison_result);
    
        // use same logic provided by reeact for shallow comparison
        // from https://github.com/facebook/react/blob/master/packages/shared/shallowEqual.js
        const shallow_comparison_result = shallowEqual(prevRest, nextRest);
        console.log(`shallow comparison`, shallow_comparison_result);
    
        return deep_comparison_result && shallow_comparison_result;
      }
    );
    

    Edit React Memo - Only Deep Compare Selected Props

        2
  •  0
  •   user103716    6 年前

    功能部件不应该使用 useMemo

    我不确定你想达到什么目的:深入比较以避免虚假的重新渲染?