每次使用相同的道具反应备忘录渲染

时间:2019-02-15 10:46:39

标签: reactjs

我试图在我的功能组件中使用React.memo。它从父级组件获取道具。但是我将相同的props传递给我的'memo'组件,每次都会渲染。当我使用React.Purecomponent时发生了同样的事情,但是当我使用shouldcomponentupdate时却没有发生:为什么?

我在初始状态下有一个切换变量。

enter image description here,当我调整窗口handleResize的大小,并重置标题时,这意味着我的false开关现在为]

enter image description here。我将toggle变量传递给了我的子组件。

enter image description here然后我从道具中拿走了。

enter image description here ..对不起,我在这个问题上有一些打字错误

2 个答案:

答案 0 :(得分:1)

您每次都传递一个 toggleHamburger道具。

事实上,这是我所见过的React应用程序中最常见的性能杀手。每次传递一个新的闭包作为事件处理程序/回调。

要解决此问题,我建议您使用useCallback()钩子,或者如果您使用的是方法,因为外部组件是一个类:

class ... {
  toggleHamburger = () => this.setState(({toggle}) => ({toggle: !toggle}));
  ...
    <HamburgerButton toggleHamburger={this.toggleHamburger} />
}

React.memo()包装的组件仅在使用相同道具调用时才会渲染一次:

const Comp = React.memo(props => {
  console.log('Rendering...');
  return props.a;
});

const props = {a: 1};
const at = document.getElementById('app');
render();
render();
render();

function render() {
  console.log('Called render()'); 
  ReactDOM.render(<Comp {...props} />, at);
}
<div id="app"></div>
<script src="//unpkg.com/react/umd/react.production.min.js"></script>
<script src="//unpkg.com/react-dom/umd/react-dom.production.min.js"></script>

答案 1 :(得分:0)

    export default class extends Component {
  shouldComponentUpdate(nextProps) {
    const { toggle } = this.props;
    return nextProps.toggle !== toggle;
  }

  render() {
    console.log('Rendering ...');
    const { toggleHamburger, toggle } = this.props;
    return (
      <svg viewBox="0 0 96 96" height="1em" onClick={toggleHamburger} {...{ style }}>
        <Motion
          style={{
            x: spring(toggle ? 1 : 0, presets.wobbly),
            y: spring(toggle ? 0 : 1, presets.wobbly)
          }}
        >
          {({ x, y }) => (
            <g
              id="navicon"
              fill="none"
              stroke="currentColor"
              strokeWidth="14"
              strokeLinecap="round"
              strokeLinejoin="round"
            >
              <line
                transform={`translate(${x * 12}, ${x * -7}) rotate(${x * 45}, 7, 26)`}
                x1="7"
                y1="26"
                x2="89"
                y2="26"
              />
              <line
                transform={`translate(${x * 12}, ${x * 7}) rotate(${x * -45}, 7, 70)`}
                x1="7"
                y1="70"
                x2="89"
                y2="70"
              />
              <line
                transform={`translate(${x * -96})`}
                opacity={y}
                x1="7"
                y1="48"
                x2="89"
                y2="48"
              />
            </g>
          )}
        </Motion>
      </svg>
    );
  }
}