使用钩子reactjs

时间:2020-06-23 12:17:13

标签: javascript reactjs

我正在学习将钩子与react结合使用,并尝试创建一个简单的网站,在其中写入2个值并将其添加到列表中。列表中的每个项目都有一个删除按钮。

由于某种原因,当我添加两行以上时,问题似乎开始了。例如,如果我添加2行,然后在开始加载的旧行上按Delete键-它要么删除它们,要么用与新行相同的值替换它们。

不知道我在做什么错,因为删除有效,直到我直接在开始处添加+2行以上。

Kinda很难解释,但是我创建了一个沙箱,可以更容易地看到问题。

删除和添加功能:

  const deleteRow = async (index, e) => {
    var data = testArr;
    data.splice(index, 1);

    setTestArr([...data]);
  };

  const addRow = async e => {
    var obj = {
      id: 1,
      start: inputFrom,
      stop: inputTo
    };

    var data = testArr;
    data.push(obj);

    setTestArr([...data]);
  };

映射功能:

{testArr.map((item, index) => (
        <div key={item.id} className="col-12">
          <div className="control-group mb-1">
            <span className="mr-2">
              {item.start} - {item.stop}
            </span>
            <input
              type="button"
              className="btn btn-light"
              value="Delete row"
              onClick={e => deleteRow(index, e)}
            />
          </div>
        </div>
      ))}

沙箱:

Edit creact-hooks-usestate-nk4cl

3 个答案:

答案 0 :(得分:3)

首先,您可能不使用var关键字,而是使用ES const || let,以确保您不会因为JS吊起而遇到意外的副作用,

秒-

var data = testArr;
data.splice(index, 1);

是非法移动,因为data与状态在内存中没有不同,它只是指针,因此您可以在setState之外修改状态

第一个选择是浅拷贝状态

let data = [...testArr];

或直接在setState

内部实现逻辑
// delete
setTestArr(prev => prev.filter((item, i) => i != index ));
// add
setTestArr(prev => [...prev, obj]);

答案 1 :(得分:3)

尝试使用以下功能:

const deleteRow = async (index, e) => {
  var data = [...testArr];
  data.splice(index, 1);
  setTestArr(data);
};

const addRow = async e => {
  setTestArr([{
   id: 1,
   start: inputFrom,
   stop: inputTo
 },...testArr]);
};

我建议您使用useCallback来定义它们。

答案 2 :(得分:3)

我将使用此删除功能:

  const deleteRow = (index, e) => {
    setTestArr(prev => {
      
      return prev.filter((e, i) => i !== index);
    });
  };

代替过滤数据,只是过滤掉我们不需要的索引。