C#列表 – 删除项目while循环/迭代

假设我有下面的代码片段:

var data=new List<string>(){"One","Two","Three"}; for(int i=0 ; i<data.Count ; i++){ if(data[i]=="One"){ data.RemoveAt(i); } } 

以下代码引发exception。

我的问题是什么是避免这种exception,并在循环中删除元素的最好办法?

如果您需要删除元素,则必须向后迭代,以便可以从列表的末尾删除元素:

 var data=new List<string>(){"One","Two","Three"}; for(int i=data.Count - 1; i > -1; i--) { if(data[i]=="One") { data.RemoveAt(i); } } 

但是,有更有效的方法来做到这一点与LINQ(如其他答案所示)。

你可以使用List<T>.RemoveAll来处理这个:

 data.RemoveAll(elem => elem == "One"); 

我遇到一个简单的解决scheme,使用foreach.ToArray()

  var data=new List<string>(){"One","Two","Three"}; foreach ( var d in data.ToArray()){ if(d =="One"){ data.Remove(d); } } 

你可以尝试ChrisF的反向迭代方法来删除你的项目。

你也可以简单地:

 List.Remove("One"); 

要么:

 List.RemoveAll(i => i == "One"); // removes all instances 

并且完成它。 遍历集合删除单个项目是没有意义的。

您也可以使用一个向前移动的循环,如:

 var data = new List<string>() { "One", "Two", "Three", "One", "One", "Four" }; for (int i = 0; i < data.Count; i++) { if (data[i] == "One") { data.RemoveAt(i--); } } 

这行data.RemoveAt(i--); 在从列表中删除项目的情况下,在循环结束时停止迭代variables的增量效应。

它将从当前迭代值的索引中删除项目,然后在删除项目之后,迭代器将被设置为比当前迭代器less一个值。 循环结束时,循环体中的增量将移动到下一个有效索引。

这是一个工作dotfiddle

(请注意,我个人使用反向循环来处理这种情况,因为国际海事组织,他们更容易理解,这里的答案只是为了显示实现它的另一种方式)

你为什么不简单地递减迭代器variables?

 var data=new List<string>(){"One","Two","Three"}; for(int i=0 ; i<data.Count ; i++){ if(data[i]=="One"){ data.RemoveAt(i); i--; // <<<<<<<<<<< } } 

这是一个肮脏的伎俩,我不知道会有什么批评呢?

 var data=new List<string>(){"One","Two","Three"}; foreach (string itm in (data.ToArray())) { if string.Compare(name, "one", true) == 0) data.Remove(name); } 

下面的一般解决scheme将生成一个副本列表并处理负向索引:

 foreach (void item_loopVariable in MyList.ToList) { item = item_loopVariable; } 
  var data = new List<string>() { "One", "Two", "Three" }; data.RemoveAll(p=>p=="One"); 
 var data=new List<string>(){"One","Two","Three"}; for(int i=0; i<data.Count; ){ if(data[i]=="One") data.RemoveAt(i); else ++i; } 

你可以使用Stack类

  Stack<string> myStack = new Stack<string>(); foreach (var item in Enumerable.Range(1,1001)) myStack.Push("Str " + item.ToString()); while (myStack.Any()) Console.WriteLine("Now {0} items in Stack, removed item is {1}",myStack.Count,myStack.Pop()); Console.ReadKey(); 

我不得不从列表中删除多个项目。 所以,我重新初始化列表计数。 还有其他更好的select吗?

 for (int i = dtList.Count - 1; dtList.Count > 0; ) { DateTime tempDate = dtList[i].Item1.Date; var selectDates = dtList.FindAll(x => x.Item1.Date == tempDate.Date); selectDates.Sort((a, b) => a.Item1.CompareTo(b.Item1)); dtFilteredList.Add(Tuple.Create(selectDates[0].Item1, selectDates[0].Item2)); dtList.RemoveAll(x => x.Item1.Date == tempDate.Date); i = dtList.Count - 1; } 
 List<string> list = new List<string>(); list.Add("sasa"); list.Add("sames"); list.Add("samu"); list.Add("james"); for (int i = list.Count - 1; i >= 0; i--) { list.RemoveAt(i); }