Method
Method

Reputation: 143

How to edit an iterator within a foreach loop

Scenario

I have a system that holds races, each race has a unique list of members on that race. (the list is a List< T > )

I want users to be able to remove a member (if they ARE this member) from the list of members on that race.

Problem

I'm trying to get the following code to work:

foreach (string item in hillracing.searchRaces(RaceID).RaceList) // Loop through List with foreach.
{
    if (item == SelectedItem)
    {
        item = null;
    }
}

I can't edit the variable because it is in a foreach loop, how would I achieve this another way?

Upvotes: 0

Views: 1088

Answers (5)

W0lfw00ds
W0lfw00ds

Reputation: 2086

Use the existing Remove()-method to search and remove the item for you:

hillracing.searchRaces(RaceID).RaceList.Remove(SelectedItem);

Upvotes: 0

Tim Schmelter
Tim Schmelter

Reputation: 460128

You can't do that in a foreach loop. If it's an IList/IList<T> which allows random access, like an array or list, you can use a for-loop:

List<string> = hillracing.searchRaces(RaceID).RaceList;
for(int i = 0; i < list.Count; i++)
{
    if(list[i] == SelectedItem)
         list[i] = null;
}

So you can't add or remove items in the foreach but you also can't replace the reference. The object refers to the original value so you could modify the object(if strings werent immutable) but you can't replace the reference itself in a foreach. This is related.

Upvotes: 0

amcdermott
amcdermott

Reputation: 1585

Using Linq you shouldn't need to loop to find the entry you want to nullify...

// Use of Single() here assumes the object definitely exists. 
// Use SingleOrDefaul() if there is a chance it might not exist.
var item = hillracing.searchRaces(RaceID)
                     .RaceList
                     .Where(x => x.Item == SelectedItem).Single();  

item = null;

Edit: Since you've changed the requirement to remove the item from the list, I think you'd just call the Remove method`with the found item. So the code becomes

// Use of Single() here assumes the object definitely exists. 
// Use SingleOrDefaul() if there is a chance it might not exist.
var item = hillracing.searchRaces(RaceID)
                     .RaceList
                     .Where(x => x.Item == SelectedItem).Single();  

hillracing.searchRaces(RaceID).RaceList.Remove(item);

Upvotes: 0

Nils O
Nils O

Reputation: 1321

You can just store it and remove it form the collection afterwards.

var toRemove = null;
foreach (string item in hillracing.searchRaces(RaceID).RaceList) // Loop through List with foreach.
{
    if (item == SelectedItem)
    {
        toRemove = item;
        break; //Can break here if you're sure there's only one SelectedItem
    }
}
hillracing.searchRaces(RaceID).Racelist.Remove(toRemove);

though in this case you could also just use hillracing.searchRaces(RaceID).Racelist.Remove(SelectedItem); and you won't use the foreach loop at all.

Upvotes: 1

Rahul Nikate
Rahul Nikate

Reputation: 6337

You can't modify collection that you are looping using foreach loop. The collection used in foreach is immutable. This is by design.

The foreach statement is used to iterate through the collection to get the information that you want, but can not be used to add or remove items from the source collection to avoid unpredictable side effects. If you need to add or remove items from the source collection, use a for loop.

Upvotes: 0

Related Questions