0

I need to delete element in an array of Object, look at my array:

I want delete the elements which have done == true, look at my script:

var items = [{text: "a", done: false}, {text: "b", done: false}, {text: "c", done: true}, {text: "d", done: true}, {text: "e", done: true}];


items.forEach((elem, index) => {
  if(items[index].done) {
    items.splice(index, 1);
  }
})

console.log(items)

But it's doesn't work.

3
  • Use a reverse loop Commented Feb 7, 2017 at 13:37
  • Possible duplicate of Remove Object from Array using JavaScript Commented Feb 7, 2017 at 13:38
  • Well the problem is that you are iterating and removing elements from array at the same time. Commented Feb 7, 2017 at 13:41

2 Answers 2

3

This will not work because your are iterating and modifying the same array. When you delete an element at index 1, the element at index 2 become index 1 but your forEach will continue to iterate and will not check the new index 1

You can simply use Array.prototype.filter()

var items = [{text: "a", done: false}, {text: "b", done: false}, {text: "c", done: true}, {text: "d", done: true}, {text: "e", done: true}];

items = items.filter(function(elem){
    return !elem.done;
});

console.log(items);

Sign up to request clarification or add additional context in comments.

Comments

2

You want to filter out things from an array. The best thing then is to use the filter method.

var items = [{text: "a", done: false}, {text: "b", done: false}, {text: "c", done: true}, {text: "d", done: true}, {text: "e", done: true}]

console.log(items.filter(o => !o.done))

The problem with your code is you are modifying the array while you are iterating over it, therefore when you remove an element all elements shift, and you skip the next element.

Check the following snippet, and how you never access the (d) element:

var items = [{text: "a", done: false}, {text: "b", done: false}, {text: "c", done: true}, {text: "d", done: true}, {text: "e", done: true}]

var itemsCopy = [{text: "a", done: false}, {text: "b", done: false}, {text: "c", done: true}, {text: "d", done: true}, {text: "e", done: true}]

items.forEach((elem, index) => {
      if (itemsCopy[index].text !== items[index].text)
      console.log('you want to access', itemsCopy[index].text, 'instead you are accessing', items[index].text)
      if(items[index].done) {
        items.splice(index, 1);
        //elem.remove();
      }
  })

Every cycle the index increase by 1, so when you remove the c element, (index 2) then index becomes 3. But since you have deleted the c, now your array looks like:

[a, b, d, e]

Therefore you are accessing element e, not d, because now d has index 2

1 Comment

This doesn't answer the OP's question (namely - he modifies the array while iterating over it)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.