【发布时间】:2019-03-24 21:29:15
【问题描述】:
我已经看到 examples 展示了如何在 React 中实现双向绑定,但没有人解释此功能实际上是如何在内部发挥作用的。
在这个来自 React 网站的 codepen example 中,如果你注释掉第 11 行:
handleChange(event) {
// this.setState({value: event.target.value});
}
您会注意到 React 如何通过确保视图不会以与数据模型不一致的方式更新来强制执行 2-way 绑定,即使在用户直接修改输入框之后也是如此。但它是如何做到的呢?
考虑到event.target.value 有用户刚刚在handleChange 范围内输入的输入,但在视图中仍然为空,这意味着在某些时候该值被 React 重置。另外,它不是简单地将值重置为空,而是根据最新的数据模型,可以通过对代码进行以下更改来测试:
constructor(props) {
super(props);
this.state = {value: ''};
this.handleChange = this.handleChange.bind(this);
this.handleSubmit = this.handleSubmit.bind(this);
this.counter = 0;
}
handleChange(event) {
if (this.counter < 3) {
this.setState({value: event.target.value});
this.counter++;
}
}
这一次,输入框改变了前三次,然后根据最后一个模型状态重置。
我的猜测如下:
- HTML 元素根据用户输入进行修改。
- “onchange”事件处理程序被触发。
- 状态未更新。
- 由于状态未更新,React 将组件的缓存 Virtual-DOM 表示与用户刚刚更改的 Real-DOM 元素进行比较。
- React 更新 Real-DOM 元素的属性,使其与其 Virtual-DOM 表示一致。
如果状态发生了变化,那么缓存的 Virtual-DOM 表示会被“弄脏”,这会触发虚拟元素的重新渲染。但是,我上面描述的其余流程仍然适用,这意味着不会创建新的 HTML 节点,只会更新现有节点的属性(假设元素类型,例如 <input>,没有t改变)。
这是我对该功能的内部机制可能的最佳猜测。如果我错了,请告诉我,如果是,问题的真正答案是什么。
谢谢!
【问题讨论】: