开发者

Removing elements of a collection that I am foreaching through

Here is some dummy c开发者_如何学JAVAode that illustrates what I want to do:

List<int> list1 = new List<int>();
//Code to fill the list
foreach(int number in list1)
{
    if(number%5==0)
    {
        list1.Remove(number);
    }
}

Assuming the test actually removes an int, it will throw an error. Is there a way of doing this in a foreach, or do I have to convert it to a for loop?


You can't remove items from a collection that you are iterating thru with a for each. I would do this...

list1 = list1.Where(l => l % 5 != 0).ToList();


The RemoveAll() method comes closest to what you want, I think:

list1.RemoveAll(i => i%5 == 0);


Actually if you want to remove the list as you state in the O.P you could do:

List<int> list1 = new List<int>();
//Code to fill the list
for(var n = 0; n < list.Count; i++)
{
    if (list[n] % 5 == 0)
    {
        list1.Remove(list[n--]);
    }
}

Edited to Add

The reason why you can't change a list while in a for each loos is as follows:

[Serializable()] 
public struct Enumerator : IEnumerator<T>, System.Collections.IEnumerator
{
    private List<T> list;
    private int index; 
    private int version;
    private T current; 

    internal Enumerator(List<T> list) {
        this.list = list; 
        index = 0;
        version = list._version;
        current = default(T);
    } 

    public void Dispose() { 
    } 

    public bool MoveNext() { 

        List<T> localList = list;

        if (version == localList._version && ((uint)index < (uint)localList._size)) 
        {
            current = localList._items[index]; 
            index++; 
            return true;
        } 
        return MoveNextRare();
    }

    private bool MoveNextRare() 
    {
        if (version != list._version) { 
            ThrowHelper.ThrowInvalidOperationException(ExceptionResource.InvalidOperation_EnumFailedVersion); 
        }

        index = list._size + 1;
        current = default(T);
        return false;
    } 

    public T Current { 
        get { 
            return current;
        } 
    }

    Object System.Collections.IEnumerator.Current {
        get { 
            if( index == 0 || index == list._size + 1) {
                 ThrowHelper.ThrowInvalidOperationException(ExceptionResource.InvalidOperation_EnumOpCantHappen); 
            } 
            return Current;
        } 
    }

    void System.Collections.IEnumerator.Reset() {
        if (version != list._version) { 
            ThrowHelper.ThrowInvalidOperationException(ExceptionResource.InvalidOperation_EnumFailedVersion);
        } 

        index = 0;
        current = default(T); 
    }

}


As far as I know, a collection cannot be modified while in a foreach loop. You need to change it to a for loop. Another way you can accomplish that is using LINQ.


You can't do it in-situ using foreach, because it invalidates the enumerator.

Either take a copy of the list and iterate over that, or use a different type of loop such as a for() loop.


You cannot modify the collection your are enumerating through using foreach. What I often do is use a for loop and go backwards through the collection, thus you can safely remove items since the length won't be affected until you move to the previous item.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜