【问题标题】:Am I understanding the Virtual Dom correctly?我是否正确理解了 Virtual Dom?
【发布时间】:2016-05-03 09:05:31
【问题描述】:

我正在对 React 程序进行基本介绍,想知道我是否正确理解了虚拟 dom 的差异。

我有这个小应用程序:

import React, { Component } from 'react';

const svgStyle = {
  border: '1px solid black'
};

const Circle =({x, y}) => (
  <circle cx={x} cy={y} r="5" />
);

class Canvas extends Component {
  constructor(props) {
    super(props);

    this.state = {
      circles: []
    };

    this.addCircle = this.addCircle.bind(this);
  }

  addCircle(e) {

    const {left: rectLeft, top: rectTop} = e.target.getBoundingClientRect();
    const {clientX, clientY} = e;

    this.setState({
      circles: this.state.circles.concat([{x: clientX - rectLeft, y: clientY - rectTop}])
    });
  }

  render() {
    var {circles} = this.state;

    return (
      <svg width="500" height="500" viewBox="0 0 500 500" onClick={this.addCircle} style={svgStyle}>
        {
          circles.map(circle => (<Circle x={circle.x} y={circle.y} r="5" />))
        }
      </svg>
    );
  }
}

export default Canvas;

我的问题是,每当我向状态对象添加一个时,所有 svg &lt;circles&gt; 都会重新渲染吗?或者 React 是否区分状态中的那些已经存在并且不需要对它们做任何事情的事实。

【问题讨论】:

标签: reactjs virtual-dom


【解决方案1】:

每当您再添加一个或更新状态时,所有&lt;circle&gt; 标记都会重新呈现。

在渲染集合 (.map) 时,React 建议使用 key 属性,其值可唯一标识正在渲染的实例。

因此,为了实现这一点,我建议向 circle 对象添加一个 id 属性,然后将其呈现为:

circles.map(circle => 
    <Circle key={circle.id} x={circle.x} y={circle.y} r="5" />
)

因此,下次 React 进行 diff 时,它知道将 &lt;Circle key="1" ... /&gt; 与影子 DOM 中的 &lt;Circle key="1" ... /&gt; 进行比较,并且仅在 DOM 发生变化时才更新它。

【讨论】:

    猜你喜欢
    • 2020-09-30
    • 1970-01-01
    • 1970-01-01
    • 2018-04-21
    • 1970-01-01
    • 2014-10-17
    • 2011-12-07
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多