реквизиты / компоненты не являютсянеизменяемый, но изменение их не будет влиять на рендерингпуть). Я хотел проверить, какое из этих 3 утверждений было правдой, поэтому я попытался разбить их все, одно за другим, чтобы увидеть, какие из них стоят.Все тестовые случаи, которые я опишу здесь, реализованы в этой закуске .
Реквизиты неизменны?
Давайте рассмотрим этот простой пример:
const style = {height: 10, width: 10, backgroundColor: "red"};
const firstItem = <View style={style} />;
firstItem.props.style = {...style, height: 100};
console.log(firstItem.props.style.height);
Если firstItem.props
был неизменным, это должно вывести 10
, поскольку firstItem.props.style = {...style, height: 100};
не будет иметь никакого эффекта.Но вместо этого выводится 100
, поэтому я должен заключить, что свойства props
компонента не являются неизменяемыми в реагировать на нативные.
Сами компоненты неизменны?
То жепрежде давайте сделаем простой тест для этого:
const secondItem = <View style={style} />;
secondItem.props = {style: {...style, height: 200}};
console.log(secondItem.props.style.height);
Опять же, это должно вывести 10
, если secondItem
было неизменяемым, но это печатает 200
.Поэтому компоненты не являются неизменяемыми в реагируют на натив.
Смена реквизита не повлияет на рендеринг?
На этот раз мне не нужно изменять код, я простонужно визуализировать эти два элемента и посмотреть, являются ли они высокими прямоугольниками или маленькими квадратами.И, как вы, возможно, уже догадались, это отрисовывает два высоких прямоугольника, а это означает, что изменение мутирующего компонента / реквизита влияет на рендеринг компонентов.
export default class App extends React.PureComponent {
render() {
return (
<View style={{ margin: 20, padding: 20, flexDirection: "row" }}>
{firstItem}
{secondItem}
</View>
);
}
}
Показывает следующее:
My questions
Is there a flaw in my test cases? Is there a difference between react and react native on how props are handled?
Finally and (maybe) most importantly, even if react native doesn't enforce props immutability, why should it be considered "dangerous" or simply bad practice to mutate it (harder to predict/debug)? In other words, why does react provide a React.cloneElement
instead of having immutable props
. Does it mean that they suggest to not mutate props, but they don't want to impose that constraint, or did I just missed something.
And ultimately, the application to a concrete use case, why is it предложил в исходном вопросе, который я связал, чтобы использовать эту форму:
React.cloneElement(child, { doSomething: this.doSomething })
Вместо (например) изменения мутирования компонента:
child.props = {...child.props, doSomething: this.doSomething }