Разница между передачей ReactElement и функцией, которая возвращает ReactElement как свойство - PullRequest
0 голосов
/ 16 февраля 2020

Какая разница между передачей ReactElement как свойства:

<RenderParam ReactElement={<Counter />} />

function RenderParam({ ReactElement }) {
  return <div>{ReactElement}</div>;
}

Первый случай

и передачей функции, которая возвращает ReactElement:

<RenderParam ReactElement={instantiatedCounter} />

function RenderParam({ ReactElement }) {
  return <div> <ReactElement /> </div> 
}

Второй случай

Я вижу различия в жизненном цикле:

  • Каждый раз, когда родительский элемент реагирует обновления, цикл монтирования Counter выполняется для второго случая:

    ReactElement changed (at RenderParam lifecycle)
    component did mount (at Counter)
    
  • Также второй случай теряет свое состояние каждый раз, когда родительский компонент рендерит.

Я не вижу, в чем разница между ними. Почему в первом случае он способен сохранить свое состояние?

Ответы [ 2 ]

1 голос
/ 16 февраля 2020

Первый пример передает элемент c JSX <Counter /> как RenderParam проп. Во втором примере используется функция instantiatedCounter, которая позволяет возвращать более динамический c элемент JSX, обычно называемый Render props .

Во втором случае вы теряете состояние, потому что React каждый раз обрабатывает ReactElement prop как только что определенный компонент, отключает старый и снова подключает его при каждом цикле рендеринга. Вам нужно вызвать опору ReactElement для получения элемента JSX в качестве возвращаемого значения:

function RenderParam({ ReactElement }) {
  return <div>{ReactElement()}</div>; 
  // not: return <div><ReactElement /></div>
}

Вы также можете определить его с помощью синтаксиса JSX <div><ReactElement /></div>. Но затем убедитесь, что instantiatedCounter является функцией stati c и не создается заново при каждом рендеринге, поэтому ссылка на объект остается неизменной:

const instantiatedCounter = () => <Counter />; 
// make it static in some way, so object reference doesn't change

export default function App() {
  // .. and remove instantiatedCounter here
  return <RenderParam ReactElement={instantiatedCounter} />
}
1 голос
/ 16 февраля 2020

Это на самом деле довольно просто, реальная вещь здесь - это время самого рендеринга.

Давайте начнем со второго случая, это на самом деле шаблон проектирования под названием Render Props, вы можете прочитать об этом здесь : https://reactjs.org/docs/render-props.html в этом случае реквизит содержит функцию, которая возвращает элемент React, что означает, что он будет оцениваться только при вызове этой функции, и, следовательно, он не всегда «живой», как в вашем первый случай.

первый случай: когда вы привязываете свою опору к элементу, она оценивается при создании родительского элемента. Это означает, что до тех пор, пока родительский элемент «жив», проп-элемент будет жив.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...