Collection was modified; enumeration operation may

2019-01-02 23:23发布

This question already has an answer here:

I'm trying to remove an item from an ArrayList and I get this Exception:
Collection was modified; enumeration operation may not execute.

Any ideas?

9条回答
对你真心纯属浪费
2楼-- · 2019-01-02 23:37

Instead of foreach(), use a for() loop with a numeric index.

查看更多
Evening l夕情丶
3楼-- · 2019-01-02 23:42

You are removing the item during a foreach, yes? Simply, you can't. There are a few common options here:

  • use List<T> and RemoveAll with a predicate
  • iterate backwards by index, removing matching items

    for(int i = list.Count - 1; i >= 0; i--) {
        if({some test}) list.RemoveAt(i);
    }
    
  • use foreach, and put matching items into a second list; now enumerate the second list and remove those items from the first (if you see what I mean)

查看更多
够拽才男人
4楼-- · 2019-01-02 23:43

Don't modify the list inside of a loop which iterates through the list.

Instead, use a for() or while() with an index, going backwards through the list. (This will let you delete things without getting an invalid index.)

var foo = new List<Bar>();

for(int i = foo.Count-1; i >= 0; --i)
{
  var item = foo[i];
  // do something with item
}
查看更多
冷血范
5楼-- · 2019-01-02 23:45

One way is to add the item(s) to be deleted to a new list. Then go through and delete those items.

查看更多
Explosion°爆炸
6楼-- · 2019-01-02 23:45

using ArrayList also you can try like this

ArrayList arraylist = ... // myobject data list

ArrayList temp = (ArrayList)arraylist.Clone();

foreach (var item in temp)
{
      if (...)
         arraylist.Remove(item);
}
查看更多
欢心
7楼-- · 2019-01-02 23:46

I like to iterate backward using a for loop, but this can get tedious compared to foreach. One solution I like is to create an enumerator that traverses the list backward. You can implement this as an extension method on ArrayList or List<T>. The implementation for ArrayList is below.

    public static IEnumerable GetRemoveSafeEnumerator(this ArrayList list)
    {
        for (int i = list.Count - 1; i >= 0; i--)
        {
            // Reset the value of i if it is invalid.
            // This occurs when more than one item
            // is removed from the list during the enumeration.
            if (i >= list.Count)
            {
                if (list.Count == 0)
                    yield break;

                i = list.Count - 1;
            }

            yield return list[i];
        }
    }

The implementation for List<T> is similar.

    public static IEnumerable<T> GetRemoveSafeEnumerator<T>(this List<T> list)
    {
        for (int i = list.Count - 1; i >= 0; i--)
        {
            // Reset the value of i if it is invalid.
            // This occurs when more than one item
            // is removed from the list during the enumeration.
            if (i >= list.Count)
            {
                if (list.Count == 0)
                    yield break;

                i = list.Count - 1;
            }

            yield return list[i];
        }
    }

The example below uses the enumerator to remove all even integers from an ArrayList.

    ArrayList list = new ArrayList() {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};

    foreach (int item in list.GetRemoveSafeEnumerator())
    {
        if (item % 2 == 0)
            list.Remove(item);
    }
查看更多
登录 后发表回答