当`setState`时,会重新生成多个dom标签

问题描述 投票:0回答:2
class Calendar extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      selected: null,
    }
  }

  generate = () => {
    console.log('generate');
    let tags = [];
    for(let i = 0; i<31; i++){
      tags.push(<div key={i} className={this.state.selected === (i+1) ? 'selected' : ''}>{i+1}</div>);
    }
    return tags;
  }

  clickHandle = (e) => {
    this.setState({
      selected: e.target.innerText
    })
  }

  render(){
    return(
      <div onClick={this.clickHandle}>
        {this.generate()}
      </div>
    )
  }
}

当我点击div时,它会调用generate()

我认为效率低下。

有没有更有效的方法从上面的代码生成多个元素?

条件

  1. 当我点击一个div时,它必须得到类selected
  2. 当我点击另一个div时,之前点击的div必须删除类selected和1。
reactjs performance
2个回答
2
投票

我发现这里存在两个妨碍预期结果的问题。当您使用DOM中的值时,您总是会得到一个字符串。由于您使用的是“===”,因此它永远不会评估为true,因此className不会更改。

clickHandle = (e) => {
    this.setState({
      selected: parseInt(e.target.innerText, 10)
    })
  }

您还应该在使用重复元素时使用键,以提高性能。

generate = () => {
    console.log('generate');
    let tags = [];
    for(let i = 0; i<31; i++){
      tags.push(<div key={'keyname'+i} className={this.state.selected === (i+1) ? 'selected' : ''}>{i+1}</div>);
    }
    return tags;
  }

0
投票

你应该给每个div一个unique key。这有助于React仅重新渲染实际具有更改的div,而其他未更改的div将被重用。

let tags = [];
for(let i = 0; i<31; i++){
  tags.push(<div key={i} className={this.state.selected === (i+1) ? 'selected' : ''}>{i+1}</div>);
}
return tags;
© www.soinside.com 2019 - 2024. All rights reserved.