在反应中设置状态问题

时间:2020-04-29 09:20:33

标签: reactjs

我只是通过开发一个搜索可用域名的应用程序来学习React,现在我想使其变得更复杂。.但是我认为我其中一个函数中的setState非常笨拙,并且非常确定这是一种性能问题,因此不能以这种形式继续使用。

我遇到的功能是onChangeWord,它每次用户在输入框中输入任何内容时都会运行。它当前正在使用map函数,因此,每次用户键入时,它都会修改words状态数组,而该数组中所有其他未修改的单词也会使用map函数&if语句进行重置。现在,我想为每个单词添加同义词(每个单词有时需要200+。),所以我认为我做的不正确。每次输入字母时,它会映射到每个单词和状态位..当然有更好的方法。

是否可以清理我的onChangeWord函数和/或更改words状态的结构方式,以便使该函数更简洁?

/// ControlPanel.js ///
export default class ControlPanel extends Component {
  state = {
    words: 
    [
      { 
        word: "",
        id: 1,
        column: 1,
        // synonymns: {
        //   all:[],
        //   selected:[]
        // }
      },
      { 
        word: "",
        id: 2,
        column: 2,
        // synonymns: {
        //   all:[],
        //   selected:[]
        // }
      }
    ]
  }

  onChangeWord = (columnId, e) => {
    const { words } = this.state
    const newWords = []
    words.map(word => {
      if(word.id == e.target.id){
        newWords.push( {word: e.target.value, id: word.id, column: columnId} ) 
      } else {
        newWords.push( {word: word.word, id: word.id, column: word.column} ) 
      } return null;
    })
    this.setState ({words: newWords})
  }

  // onAddWord = id => {...}
  // onRemoveWord = id => {...}
  // combineWords() {
  // ...etc
  // render() {...}
}

//////////////

/// WORD.js //

const Word = ({onRemoveWord, wordId, onChangeWord, columnId}) => {
  return (
    <div>
       <input 
          type="text"
          name="word" 
          id={wordId} 
          onChange={(e) => onChangeWord(columnId, e)} 
        /> 
        <span onClick={() => {onRemoveWord(wordId)}} className="deletebtn">-</span>
    </div>
  )
}

/////////////

3 个答案:

答案 0 :(得分:1)

您没有使用columnId检查要标识的单词。

重构

onChangeWord = (columnId, e) => {
    const { words } = this.state
    const newWords = []
    words.map(word => {
      if(word.id == e.target.id){
        newWords.push( {word: e.target.value, id: word.id, column: columnId} ) 
      } else {
        newWords.push( {word: word.word, id: word.id, column: word.column} ) 
      } return null;
    })
    this.setState ({words: newWords})
  }

onChangeWord = (columnId, e) => {
    const { words } = this.state
    const newWords = words.map(word => {
      if(word.id === columnId){
        return {...word, 'word': e.target.value} 
      }
      return word
    })
    this.setState ({words: newWords})
  }

答案 1 :(得分:1)

具有固定ID的单词是否总是在同一列中?如果是这样,您可以按列存储单词,然后在该子集上运行地图。对于过去的“键入内容并更新”输入,我使用的是onBlur而不是onChange,它会在单元格失去焦点而不是键入内容之后发生。

如果您想在键入时进行更新,但不一定要在每次击键时都进行更新,并且不必在失去焦点时进行更新,那么我会考虑对计时器进行更新,该计时器在每次键入内容时都会重置。这样可以提供一些缓冲。

答案 2 :(得分:1)

希望它有帮助

请注意,您可能不需要发送columnId,也许您可​​以从...w收到它


    onChangeWord = (columnId, e) => this.setState ({
             words: this.state.words.map(w => w.id == e.target.id 
                ? {...w, word: e.target.value, column: columnId} 
                : w
   })