在C#中删除项目时重置HashSet

aHu*_*ter 26 c# hashset

我在C#中有一个hashset,如果在迭代通过hashset时遇到条件,我将删除它,并且不能使用foreach循环执行此操作,如下所示.

foreach (String hashVal in hashset) 
{
     if (hashVal == "somestring") 
     {
            hash.Remove("somestring");
     }
}
Run Code Online (Sandbox Code Playgroud)

那么,如何在迭代时删除元素?

adr*_*nks 51

改为使用HashSet 的RemoveWhere方法:

hashset.RemoveWhere(s => s == "somestring");
Run Code Online (Sandbox Code Playgroud)

您指定条件/谓词作为方法的参数.将删除散列集中与谓词匹配的任何项.

这避免了在迭代过程中修改hashset的问题.


回应你的评论:

's'表示从hashset中计算的当前项.

上面的代码相当于:

hashset.RemoveWhere(delegate(string s) {return s == "somestring";});
Run Code Online (Sandbox Code Playgroud)

要么:

hashset.RemoveWhere(ShouldRemove);

public bool ShouldRemove(string s)
{
    return s == "somestring";
}
Run Code Online (Sandbox Code Playgroud)

编辑: 我刚刚发生了一些事情:因为HashSet是一个不包含重复值的集合,所以只需调用即可hashset.Remove("somestring").没有必要在循环中执行它,因为永远不会有多个匹配.


Fre*_*örk 8

使用枚举器循环遍历集合时,无法从集合中删除项目.解决这个问题的两种方法是:

  • 使用常规索引for循环在集合上向后循环(我相信在a的情况下不是一个选项HashSet)
  • 循环遍历集合,将要删除的项添加到另一个集合,然后遍历"待删除"集合并删除项目:

第二种方法的示例:

HashSet<string> hashSet = new HashSet<string>();
hashSet.Add("one");
hashSet.Add("two");

List<string> itemsToRemove = new List<string>();
foreach (var item in hashSet)
{
    if (item == "one")
    {
        itemsToRemove.Add(item);
    }
}

foreach (var item in itemsToRemove)
{
    hashSet.Remove(item);
}
Run Code Online (Sandbox Code Playgroud)


jav*_*red 6

我会避免使用两个foreach循环 - 一个foreach循环就足够了:

HashSet<string> anotherHashSet = new HashSet<string>();
foreach (var item in hashSet)
{
    if (!shouldBeRemoved)
    {
        anotherSet.Add(item);
    }
}
hashSet = anotherHashSet;
Run Code Online (Sandbox Code Playgroud)