从数组中删除项目-父级子级-React挂钩

时间:2020-06-07 03:24:12

标签: arrays reactjs react-hooks parent-child

我正在尝试从数组中删除一项。

一个简单的示例,父级创建子级数组。

const Parent = () => {

    const [content, setContent] = useState([]);

    useEffect(() => {});

    const addContent = event => {
        setContent(content => content.concat(
          <Child key={content.length} id={content.length} removeItem={(id) => removeContent(id)}/>
        ));
    }

    function removeContent (id) {
        setContent(content.slice(id, 0));
    }

    return(
        <div onClick={(event) => addContent(event)}>
            {content}
        </div>
    )
}

孩子有一个删除按钮。

const Child = ({id, removeItem}) => {

    remove = event => {
        removeItem(id);
    }

    return(
       <button onClick={(event) => remove(event)}>
            Remove
       </button>
    )
}

问题

假设我在我的数组中创建了4个子代:
[0:{child1},1:{child2},2:{child3},3:{child4}]

我将通过点击child2的删除按钮来删除child3(索引2)。

它转到我的父removeContent,但我的数组如下所示:
[0:{child1},1:{child2}]

然后删除我的整个数组。有人知道为什么吗?

2 个答案:

答案 0 :(得分:1)

您的代码中几乎没有问题

1)您正在单击一次监听添加/删除两个事件

<div onClick={(event) => addContent(event)}> // <---- listening to add
      // Arry of child which has remove , so on click it will trigger both remove and add (for parent)
      {content} 
     // so 
</div>

// {content}  should be out side of that div

2) slice返回新的子数组,该数组的切片将不提供具有已删除id的数组,相反,您可以使用filter(带有id)或splice(带有索引) )

3)您不应在状态( Do Read )内存储jsx


工作片段:

您可以运行以下代码段并查看代码更改。

const { useState , useEffect } = React;

const Child = ({id, index, removeItem}) => {

    return(
       <button onClick={() => removeItem(index)}>
            {id} - Remove
       </button>
    )
}

var contentId = 0;
const Parent = () => {

    const [content, setContent] = useState([]);

    useEffect(() => {});

    const addContent = event => {
        contentId++;
        setContent(content => [...content , contentId]);
    }

    function removeContent (index) {
        let clone = [...content]
        clone.splice(index, 1)
        setContent(clone);
    }

    return(<div>
        <div onClick={(event) => addContent(event)}>
            Add Content
        </div>
        {
          content.map((id,i) => 
            <Child key={id} id={id} index={i} removeItem={removeContent}/>
          )
        }
        </div>
    )
}

ReactDOM.render(<Parent />, document.getElementById('react-root'));
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.8.4/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.8.4/umd/react-dom.production.min.js"></script>
<div id="react-root"></div>

答案 1 :(得分:0)

之所以发生这种情况,是因为您使用切片来删除项目。您的分片采用两个值,第一个是开始,另一个是结束。您从id索引开始,然后从右侧删除所有索引,然后转到第0个索引。因此,从头到尾删除所有项目。

arr.slice([开始[,结束]])

使用Array.filter方法是一种更好的解决方案,可以从数组中删除项目,而且这种解决方案也是一成不变的。

//用于从现有数组中删除所选数组索引的函数。

const removeSelectedItem = (arr, index) => {
   return arr.filter((el, i) => index !== i)
}

此功能将从阵列中删除选定的项目。 arr->您的数组。 index->​​要删除的项目的索引。

希望这能回答您的问题。