Unfortunately every language with dynamic lists do not have a corresponding iterator that can remove an item easily. I have seen quite a few bugs introduced by the following idiom that I like to see avoided if at all possible.
for (int i = 0; i < list.Length; ++i) {
if (list[i].Name == 'Nasty') {
list.RemoveAt(i);
--i;
}
}
Modifying the index variable inside the loop has always been a code smell. It is among the greatest ways to introduce a bug, especially during maintenance. Plus it can get quite messy if there are several conditions that an item needs to be removed on.
for (int i = 0; i < list.Length; ++i) {
if (list[i].Name == 'Nasty') {
list.RemoveAt(i);
--i;
} else if (list[i].Name == 'Dirty') {
list.RemoveAt(i);
--i;
} else if (list[i].Name == 'Smelly') {
list.RemoveAt(i);
--i;
}
}
The above sample is still trivial, so you can imagine how messy it could get. Lets consider a different approach. What would the first sample look like if we iterated through the loop backwards?
for (int list.Length - 1; i >= 0; --i) {
if (list[i].Name == 'Nasty') {
list.RemoveAt(i);
}
}
We do not need to modify the index on item removal because any shifted items have already been processed. This scales up to our second example nicely too.
for (int list.Length - 1; i >= 0; --i) {
if (list[i].Name == 'Nasty') {
list.RemoveAt(i);
} else if (list[i].Name == 'Dirty') {
list.RemoveAt(i);
} else if (list[i].Name == 'Smelly') {
list.RemoveAt(i);
}
}
Going backwards through the list looks cleaner, and it reduces the bug potential because we are not modifying the index variable.