2014-11-28 3 views
7

У меня есть список, содержащий некоторые объекты, и вы хотите использовать LINQ для удаления определенного элемента, но я не уверен, как это сделать.Удалить определенный элемент из списка, используя LINQ

foreach (var someobject in objectList) 
{ 
    if (someobject.Number == 1) // There will only one item where Number == 1. 
    { 
     list.remove(someobject) 
    } 
} 
+2

Итак, вы код не работает или что? –

+0

Вопреки тому, что вы утверждаете, ваш текущий код вообще не связан с LINQ. У вас есть конкретные причины для желания/необходимости решения на основе LINQ? Или может быть приемлемо любое другое эффективное решение? – stakx

+1

@VsevolodGoloviznin: приведенный выше код не может работать, потому что он содержит синтаксические ошибки - 'list.remove (someobject)'. – stakx

ответ

27

вас cannot use a foreach to remove items при перечислении, вы получаете исключение во время выполнения.

Вы можете использовать List.RemoveAll:

list.RemoveAll(x => x.Number == 1); 

или, если это на самом деле не List<T> но любая последовательность, LINQ:

list = list.Where(x => x.Number != 1).ToList(); 

Если вы уверены, что есть только один элемент с этим номером или вы хотите удалить один элемент в максимуме, вы можете использовать подход для петли, предложенный в другом ответе или этом:

var item = list.FirstOrDefault(x => x.Number == 1); 
if(item ! = null) list.Remove(item); 

Ссылка на другой вопрос, который я опубликовал, предполагает, что вы можете изменить коллекцию во время перечисления в C# 4 и более поздних версиях. Нет, ты не можешь. That applies only to the new concurrent collections.

+2

В этом случае вы можете использовать foreach, так как есть только один элемент для удаления. Просто убедитесь, что вы используете break для выхода из цикла после удаления элемента, иначе вы получите исключение на следующей итерации. Тем не менее, я думаю, что решение с RemoveAll() более элегантно. – haagel

2

Вы не можете использовать foreach для удаления предмета из коллекции. Это вызовет исключение, которое будет изменено в коллекции.

Вы можете выполнить его для

for (int i=objectList.Count-1; i>=0 ; i--) 
{ 
    if (objectList[i].Number == 1) // there will only one item with Number = 1 
    { 
     objectList.Remove(objectList[i]); 
    } 
} 

Другое дело использовать Remove/RemoveAll как Tim Schmelter шоу.

+0

Как указано в другом месте, если вы счастливы «ломать» после того, как найдете совпадение, нет причин переключать цикл foreach на цикл 'for'. – Rawling

+1

@ Rawling еще один парень добавил заявление о разрыве. Во всяком случае, ответ в начале тоже был не очень хорош. – mybirthname

-1

можно удалить в индекс, если значение соответствует критериям

for (int i=0; i < objectList.Count; i ++) 
{ 
    if (objectList[i].Number == 1) // there will only one item with Number = 1 
    { 
     objectList.RemoveAt[i]; 
    } 
} 
1

Вы можете использовать цикл Еогеасп, чтобы удалить элемент из списка. Важно использовать break, чтобы остановить цикл после удаления элемента. Если цикл продолжается после удаления элемента из списка, будет выбрано исключение.

foreach (var someobject in objectList) 
{ 
    if (someobject.Number == 1) // There will only one item where Number == 1 
    { 
     objectList.remove(someobject); 
     break; 
    } 
} 

Однако это будет ТОЛЬКО работа, если есть только один объект, который вы хотите удалить, как в вашем случае.