删除对象数组中的所有子元素

3

var arr = [{
  "id": "1",
  "name": "News",
}, {
  "id": "3",
  "parent": "1",
  "name": "News 2"
}, {
  "id": "5",
  "parent": "3",
  "name": "News",
}, {
  "id": "7",
  "parent": "5",
  "name": "News 2"
}, {
  "id": "15",
  "name": "News 2"
}, {
  "id": "20",
  "name": "News 2"
}];

var deleted_id = 1;

for (var i = 0; i < arr.length; i++) {
  if (arr[i].parent == deleted_id) {
    arr.splice(i, 1);
  } else continue;
}

我需要删除id为1的项目。同时,我还需要删除所有父级字段与被删除项目id相同的子级。

请注意,id为3的项目是id为5的项目的父级,而id为5的项目是id为7的项目的父级。它们也都应该被删除。

由于存在深层级别,因此结果应该是:

[{
  "id": "15",
  "name": "News 2"
}, {
  "id": "20",
  "name": "News 2"
}]


在进行比较之前,您应该检查父级是否存在。此外,您应该缓存数组的长度,因为您在for循环中更改了长度。continue语句也是完全多余的。 - Shilly
5个回答

3
首先,您应该找到层次关系。然后根据要删除的id,进入其子级并与父级一起删除。

var arr = [{"id": "1", "name": "News", }, {"id": "3", "parent": "1", "name": "News 2"}, {"id": "5", "parent": "3", "name": "News", }, {"id": "7", "parent": "5", "name": "News 2"}, {"id": "15", "name": "News 2"}, {"id": "20", "name": "News 2"}];

console.clear();

var children = {};
arr.forEach(function (item) {
 if (item.parent)
  children[item.parent] = (children[item.parent] || []).concat(item.id);
});
function deleteItem(id) {
 if (children[id])
  children[id].forEach(deleteItem)
 var index = arr.findIndex(i => i.id === id);
 if (index >= 0)
  arr.splice(index, 1);
}

deleteItem('1')
console.log(arr);


1
该建议首先构建一棵树,然后获取一个要删除的id数组。接着应用过滤器,只获取不在列表中的那些。

var arr = [{ "id": "1", "name": "News", }, { "id": "3", "parent": "1", "name": "News 2" }, { "id": "5", "parent": "3", "name": "News", }, { "id": "7", "parent": "5", "name": "News 2" }, { "id": "15", "name": "News 2" }, { "id": "20", "name": "News 2" }],
    id = '1',
    idsToDelete = function (data) {
        var tree = {}, ids = {};
        data.forEach(function (a, i) {
            tree[a.id] = { id: a.id, children: tree[a.id] && tree[a.id].children };
            if (a.parent) {
                tree[a.parent] = tree[a.parent] || {};
                tree[a.parent].children = tree[a.parent].children || [];
                tree[a.parent].children.push(tree[a.id]);
            }
        });
        [tree[id]].forEach(function iter(a) {
            ids[a.id] = true;
            a.children && a.children.forEach(iter);
        });
        return ids;
    }(arr);

arr = arr.filter(function (a) { return !idsToDelete[a.id]; });

console.log(arr);


1

请尝试这个Fiddle: https://jsfiddle.net/58buvybn/

以下是代码:

var arr = [{
        "id": "1",
        "name": "News",
        }, {
        "id": "3",
        "parent": "1",
        "name": "News 2"
        }, {
        "id": "5",
        "parent": "3",
        "name": "News",
        }, {
        "id": "7",
        "parent": "5",
        "name": "News 2"
        }, {
        "id": "15",
        "name": "News 2"
        }, {
        "id": "20",
        "name": "News 2"
    }];

    var deleted_id = 1;
    var foundIds = [];
    var findIds = function(delId) {
        var item = arr.find(function(x) { 
            return x.id == delId;
        });

        if (foundIds.indexOf(item.id) === -1) {
            foundIds.push(item.id);            
        }

        var children = arr.filter(function(x) { 
            return x.parent == item.id;
        });

        children.forEach(function(it) {
            findIds(it.id);    
        });
    }
    findIds(deleted_id);
    var newArr = arr.filter(function(x) {
        return foundIds.indexOf(x.id) === -1;
    });
    console.log(newArr);

0

我想这对你来说会有效。

var arr =  [{  
      id:1,
      name:"News",
   },
   {  
      id:3,
      parent:1,
      name:"News 2"
   },
 {  
      id:"5",
      parent:3,
      name:"News",
   },
   {  
      id:7,
      parent:5,
      name:"News 2"
   },
 {  
      id:15,
      name:"News 2"
   },
 {  
      id:20,
      name:"News 2"
   }];

var deleted_id = 5;

for (var i = 0; i < arr.length; i++) {
  if(arr[i].hasOwnProperty('parent')) {        
    if (arr[i].parent == deleted_id) {
      arr.splice(i, 1);
      arr.splice(arr[i].parent, 1);
    }
  } else continue;
}
console.log(arr);


我只有一个第一级的ID。我需要删除此ID的所有子级,以及所有深度级别上的子级。 - marcos

0
var
    arr = [{
        "id": "1",
        "name": "News"
    }, {
        "id": "3",
        "parent": "1",
        "name": "News 2"
    }, {
        "id": "5",
        "parent": "3",
        "name": "News"
    }, {
        "id": "7",
        "parent": "5",
        "name": "News 2"
    }, {
        "id": "15",
        "name": "News 2"
    }, {
        "id": "20",
        "name": "News 2"
    }];


arr = arr.reduce(function collectItemsBySkippingIds (collector, item) {
    var
        unskippedItemList = collector.unskippedItemList,
        skipItemByIdList  = collector.skipItemByIdList,

        isSkipViaId     = (skipItemByIdList.indexOf(item.id)      >= 0),
        isSkipViaParent = (skipItemByIdList.indexOf(item.parent)  >= 0);

    if (isSkipViaId || isSkipViaParent) {
        if (isSkipViaParent) {
            skipItemByIdList.push(item.id);
        }
    } else {
        unskippedItemList.push(item);
    }
    return collector;

}, {

    unskippedItemList : [],
    skipItemByIdList  : ["1"]

}).unskippedItemList;


console.log("arr : ", arr);

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接