React.memo行为

时间:2019-04-16 14:00:51

标签: javascript reactjs

请考虑以下简单组件:

import React, { Fragment, memo } from 'react';

function Parent(props) {
  return (
    <Fragment>
      <Child {...props} />
      <Child foobar={props.foobar} />
    </Fragment>
  );
}

export default memo(Parent);
import React, { memo } from 'react';

function Child({ foobar }) {
  return (
    <p>{foobar}</p>
  );
}

export default memo(Child);

据我了解,将组件包装在React.memo()中将确保仅在其道具发生更改时才重新渲染该组件。

因此,除非传递给“父母”的任何道具发生变化,否则该组件及其整个子系都不会重新呈现。

但是,它的两个孩子呢?可以理解的是,如果“ props.fooobar”发生变化,它们都会被重新渲染。但是,如果“ props.somethingElse”被更改怎么办?其中哪个将在此处重新渲染?

1 个答案:

答案 0 :(得分:1)

如果为fooobar组件提供的除Parent以外的其他道具发生变化,Parent组件将被重新渲染,但是第一个Child组件也将被重新渲染。由于已将所有道具都交给了父母,因此其道具也将发生变化。

示例

const { memo, Fragment } = React;

const Parent = memo(props => {
  console.log("Rendered Parent");
  return (
    <Fragment>
      <Child {...props} />
      <Child foobar={props.foobar} />
    </Fragment>
  );
});

const Child = memo(({ foobar }) => {
  console.log("Rendered Child");
  return <p>{foobar}</p>;
});

class App extends React.Component {
  state = {
    foobar: "foo",
    bazqux: "baz"
  };

  componentDidMount() {
    setTimeout(() => this.setState({ foobar: "bar" }), 1000)
    setTimeout(() => this.setState({ bazqux: "qux" }), 2000)
  }

  render() {
    const { foobar, bazqux } = this.state;

    return <Parent foobar={foobar} bazqux={bazqux} />;
  }
}

ReactDOM.render(<App />, document.getElementById("root"));
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>

<div id="root"></div>