使用useState在状态更改时不进行重新渲染

时间:2020-02-29 18:51:02

标签: javascript reactjs state react-hooks virtual-dom

我正在尝试创建一个测验应用程序,用户可以在其中向动态表单添加多个问题。在此表格中,有用户可以根据需要添加或删除的问题组件。当用户单击新问题处理程序(handleNewQuestion)时,新问题将以组件状态连接到问题数组上。

python 3.8.1

我遇到的问题是,每当我尝试使用删除问题处理程序(handleRemoveQuestion)删除问题时,它总是删除错误的问题。尝试解决此问题时,我在控制台中记录了问题数组的状态,发现新问题不在该数组中,而且根据单击的问题组件,我还会得到不同的结果。您可以在提供的图像中看到我得到的结果。

quiz form with 2 questions

基本上,发生的事情是,我尝试删除控制台所依赖的问题组件显示的问题数组处于不同的状态。例如,当我尝试删除第一个问题组件时,我得到一个空数组,而当我单击第二个问题组件时,我得到一个包含一个元素的数组。即使呈现了多个问题,如果我尝试删除第一个问题,我仍然会得到一个空数组。

我不知道为什么会这样,如果有人可以解释这里发生的事情,我将不胜感激。

欢呼!

1 个答案:

答案 0 :(得分:2)

如果要修改数组(除了添加数组之外的任何其他方式),都不能使用该key。来自the documentation

如果项的顺序可能更改,我们不建议使用索引作为键。这可能会对性能产生负面影响,并可能导致组件状态出现问题。查阅Robin Pokorny的文章中的in-depth explanation on the negative impacts of using an index as a key

(我的重点)

此外,请注意,您对setQuestions的电话通话不会对现有问题更新count,这似乎是一个问题。

为您的问题分配唯一的ID,并在删除问题时使用这些ID。如果问题本质上没有唯一的ID,则可以给他们一个方法是在提供“下一个” ID的组件外部使用变量:

let nextQuestionId = 1;

const YourComponent = props => {
    // ...
    const handleNewQuestion = () => {
      setQuestions([
         ...questions,
         <Question
            key={nextQuestionId++}
            count={questions.length}
            formData={formData}
            setFormData={setFormData}
            handleRemoveQuestion={handleRemoveQuestion}
         />
      ]);
   };

   const removeQuestion = id => {
       setQuestions(questions.filter(q => q.id !== id));
   };
};

该示例未解决count问题。如果确实需要计算问题,则在添加/删除时必须重新创建所有问题。我将其留给读者作为练习,希望您实际上在count上确实不需要Question ...